diff mbox series

[RFC,BlueZ,1/1] Added GDBusMethod to notify one device of characteristic change

Message ID 20210817172909.18630-2-bernie@allthenticate.net (mailing list archive)
State Superseded
Headers show
Series method to notify/indicate to one device | expand

Commit Message

Bernie Conrad Aug. 17, 2021, 5:29 p.m. UTC
Implementation of the method and modification of the dbus method table. 

---
 src/gatt-database.c | 93 +++++++++++++++++++++++++++++++++++++++++++++
 1 file changed, 93 insertions(+)

Comments

bluez.test.bot@gmail.com Aug. 17, 2021, 5:57 p.m. UTC | #1
This is automated email and please do not reply to this email!

Dear submitter,

Thank you for submitting the patches to the linux bluetooth mailing list.
This is a CI test results with your patch series:
PW Link:https://patchwork.kernel.org/project/bluetooth/list/?series=532875

---Test result---

Test Summary:
CheckPatch                    FAIL      0.44 seconds
GitLint                       PASS      0.10 seconds
Prep - Setup ELL              PASS      40.37 seconds
Build - Prep                  PASS      0.10 seconds
Build - Configure             PASS      7.10 seconds
Build - Make                  PASS      176.64 seconds
Make Check                    PASS      8.44 seconds
Make Distcheck                PASS      208.03 seconds
Build w/ext ELL - Configure   PASS      7.17 seconds
Build w/ext ELL - Make        PASS      166.08 seconds

Details
##############################
Test: CheckPatch - FAIL
Desc: Run checkpatch.pl script with rule in .checkpatch.conf
Output:
Added GDBusMethod to notify one device of characteristic change
WARNING:LONG_LINE: line length of 122 exceeds 80 columns
#18: FILE: src/gatt-database.c:3619:
+											DBusMessage *msg, void *user_data)

WARNING:LONG_LINE: line length of 110 exceeds 80 columns
#81: FILE: src/gatt-database.c:3682:
+												 client_path);

WARNING:LONG_LINE: line length of 98 exceeds 80 columns
#86: FILE: src/gatt-database.c:3687:
+								device_get_address(client_device),

WARNING:LONG_LINE: line length of 107 exceeds 80 columns
#87: FILE: src/gatt-database.c:3688:
+								btd_device_get_bdaddr_type(client_device));

- total: 0 errors, 4 warnings, 105 lines checked

NOTE: For some of the reported defects, checkpatch may be able to
      mechanically convert to the typical style using --fix or --fix-inplace.

"[PATCH] Added GDBusMethod to notify one device of characteristic" has style problems, please review.

NOTE: Ignored message types: COMMIT_MESSAGE COMPLEX_MACRO CONST_STRUCT FILE_PATH_CHANGES MISSING_SIGN_OFF PREFER_PACKED SPDX_LICENSE_TAG SPLIT_STRING SSCANF_TO_KSTRTO

NOTE: If any of the errors are false positives, please report
      them to the maintainer, see CHECKPATCH in MAINTAINERS.


##############################
Test: GitLint - PASS
Desc: Run gitlint with rule in .gitlint

##############################
Test: Prep - Setup ELL - PASS
Desc: Clone, build, and install ELL

##############################
Test: Build - Prep - PASS
Desc: Prepare environment for build

##############################
Test: Build - Configure - PASS
Desc: Configure the BlueZ source tree

##############################
Test: Build - Make - PASS
Desc: Build the BlueZ source tree

##############################
Test: Make Check - PASS
Desc: Run 'make check'

##############################
Test: Make Distcheck - PASS
Desc: Run distcheck to check the distribution

##############################
Test: Build w/ext ELL - Configure - PASS
Desc: Configure BlueZ source with '--enable-external-ell' configuration

##############################
Test: Build w/ext ELL - Make - PASS
Desc: Build BlueZ source with '--enable-external-ell' configuration



---
Regards,
Linux Bluetooth
Luiz Augusto von Dentz Aug. 17, 2021, 11:25 p.m. UTC | #2
Hi Bernie,

On Tue, Aug 17, 2021 at 10:30 AM Bernie Conrad <bernie@allthenticate.net> wrote:
>
> Implementation of the method and modification of the dbus method table.
>
> ---
>  src/gatt-database.c | 93 +++++++++++++++++++++++++++++++++++++++++++++
>  1 file changed, 93 insertions(+)
>
> diff --git a/src/gatt-database.c b/src/gatt-database.c
> index 99c95f2d6..7e6b70a80 100644
> --- a/src/gatt-database.c
> +++ b/src/gatt-database.c
> @@ -3615,6 +3615,93 @@ static DBusMessage *manager_unregister_app(DBusConnection *conn,
>         return dbus_message_new_method_return(msg);
>  }
>
> +static DBusMessage *notify_characteristic_changed(DBusConnection *conn,
> +                                                                                       DBusMessage *msg, void *user_data)
> +{
> +       struct btd_gatt_database *database = user_data;
> +       uint8_t *value = NULL;
> +       int value_len = 0;
> +       DBusMessageIter args;
> +       DBusMessageIter array;
> +       const char *characteristic_path;
> +       const char *client_path;
> +       const char *application_path;
> +       struct svc_match_data match_data;
> +       const char *sender = dbus_message_get_sender(msg);
> +       struct gatt_app *app;
> +       struct external_service *service;
> +       struct external_chrc *chrc;
> +       struct notify notify;
> +       struct device_state *client_state;
> +       struct btd_device *client_device;
> +
> +       if (!dbus_message_iter_init(msg, &args))
> +               return btd_error_invalid_args(msg);
> +
> +       if (dbus_message_iter_get_arg_type(&args) != DBUS_TYPE_OBJECT_PATH)
> +               return btd_error_invalid_args(msg);
> +       dbus_message_iter_get_basic(&args, &application_path);
> +
> +       dbus_message_iter_next(&args);
> +       if (dbus_message_iter_get_arg_type(&args) != DBUS_TYPE_OBJECT_PATH)
> +               return btd_error_invalid_args(msg);
> +       dbus_message_iter_get_basic(&args, &client_path);
> +
> +       dbus_message_iter_next(&args);
> +       if (dbus_message_iter_get_arg_type(&args) != DBUS_TYPE_OBJECT_PATH)
> +               return btd_error_invalid_args(msg);
> +       dbus_message_iter_get_basic(&args, &characteristic_path);
> +
> +       dbus_message_iter_next(&args);
> +       if (dbus_message_iter_get_arg_type(&args) != DBUS_TYPE_ARRAY)
> +               return btd_error_invalid_args(msg);
> +
> +
> +       dbus_message_iter_recurse(&args, &array);
> +       dbus_message_iter_get_fixed_array(&array, &value, &value_len);
> +
> +       match_data.path = application_path;
> +       match_data.sender = sender;
> +       app = queue_find(database->apps, match_app, &match_data);
> +       if (!app)
> +               return btd_error_does_not_exist(msg);
> +
> +
> +       service = queue_find(app->services, match_service_by_chrc,
> +                                         characteristic_path);
> +       if (!service)
> +               return btd_error_does_not_exist(msg);
> +
> +
> +       chrc = queue_find(service->chrcs, match_chrc, characteristic_path);
> +       if (!chrc)
> +               return btd_error_agent_not_available(msg);
> +
> +
> +       client_device = btd_adapter_find_device_by_path(database->adapter,
> +                                                                                                client_path);
> +       if (!client_device)
> +               return btd_error_does_not_exist(msg);
> +
> +       client_state = find_device_state(database,
> +                                                               device_get_address(client_device),
> +                                                               btd_device_get_bdaddr_type(client_device));
> +       if (!client_state)
> +               return btd_error_does_not_exist(msg);
> +
> +
> +       notify.handle = gatt_db_attribute_get_handle(chrc->attrib);
> +       notify.ccc_handle = gatt_db_attribute_get_handle(chrc->ccc);
> +       notify.database = database;
> +       notify.value = value;
> +       notify.len = value_len;
> +       notify.conf = conf_cb;
> +
> +       send_notification_to_device(client_state, &notify);
> +       DBG("Notification/Indication sent to %s.", client_path);
> +       return dbus_message_new_method_return(msg);
> +}
> +
>  static const GDBusMethodTable manager_methods[] = {
>         { GDBUS_ASYNC_METHOD("RegisterApplication",
>                                         GDBUS_ARGS({ "application", "o" },
> @@ -3623,6 +3710,12 @@ static const GDBusMethodTable manager_methods[] = {
>         { GDBUS_ASYNC_METHOD("UnregisterApplication",
>                                         GDBUS_ARGS({ "application", "o" }),
>                                         NULL, manager_unregister_app) },
> +       { GDBUS_ASYNC_METHOD("NotifyCharacteristicChanged",
> +                                       GDBUS_ARGS({"application", "o" },
> +                                       { "device", "o" },
> +                                       { "characteristic_path", "o"},
> +                                       { "value", "ay"}),
> +                                       NULL, notify_characteristic_changed) },

I don't think this will gonna fly, we should actually emit for the
server object and not directly to the device so I rather have a
different property e.g. object, array{byte} DeviceValue, that said
this is a bit of a layer violation since the GATT layer should be in
controller of things like device address, etc, in fact it doesn't know
which devices are subscribed to its CCC. In zephyr the way we handled
this was to push this to the application by having it handling the CCC
attribute, that said I think that can create non-compliant
implementation of CCC so Im not sure if we should do that either,
anyway we could block the DeviceValue notification if the device set
is not in fact subscribed.

>         { }
>  };
>
> --
> 2.17.1
>
diff mbox series

Patch

diff --git a/src/gatt-database.c b/src/gatt-database.c
index 99c95f2d6..7e6b70a80 100644
--- a/src/gatt-database.c
+++ b/src/gatt-database.c
@@ -3615,6 +3615,93 @@  static DBusMessage *manager_unregister_app(DBusConnection *conn,
 	return dbus_message_new_method_return(msg);
 }
 
+static DBusMessage *notify_characteristic_changed(DBusConnection *conn,
+											DBusMessage *msg, void *user_data)
+{
+	struct btd_gatt_database *database = user_data;
+	uint8_t *value = NULL;
+	int value_len = 0;
+	DBusMessageIter args;
+	DBusMessageIter array;
+	const char *characteristic_path;
+	const char *client_path;
+	const char *application_path;
+	struct svc_match_data match_data;
+	const char *sender = dbus_message_get_sender(msg);
+	struct gatt_app *app;
+	struct external_service *service;
+	struct external_chrc *chrc;
+	struct notify notify;
+	struct device_state *client_state;
+	struct btd_device *client_device;
+
+	if (!dbus_message_iter_init(msg, &args))
+		return btd_error_invalid_args(msg);
+
+	if (dbus_message_iter_get_arg_type(&args) != DBUS_TYPE_OBJECT_PATH)
+		return btd_error_invalid_args(msg);
+	dbus_message_iter_get_basic(&args, &application_path);
+
+	dbus_message_iter_next(&args);
+	if (dbus_message_iter_get_arg_type(&args) != DBUS_TYPE_OBJECT_PATH)
+		return btd_error_invalid_args(msg);
+	dbus_message_iter_get_basic(&args, &client_path);
+
+	dbus_message_iter_next(&args);
+	if (dbus_message_iter_get_arg_type(&args) != DBUS_TYPE_OBJECT_PATH)
+		return btd_error_invalid_args(msg);
+	dbus_message_iter_get_basic(&args, &characteristic_path);
+
+	dbus_message_iter_next(&args);
+	if (dbus_message_iter_get_arg_type(&args) != DBUS_TYPE_ARRAY)
+		return btd_error_invalid_args(msg);
+
+
+	dbus_message_iter_recurse(&args, &array);
+	dbus_message_iter_get_fixed_array(&array, &value, &value_len);
+
+	match_data.path = application_path;
+	match_data.sender = sender;
+	app = queue_find(database->apps, match_app, &match_data);
+	if (!app)
+		return btd_error_does_not_exist(msg);
+
+
+	service = queue_find(app->services, match_service_by_chrc,
+					  characteristic_path);
+	if (!service)
+		return btd_error_does_not_exist(msg);
+
+
+	chrc = queue_find(service->chrcs, match_chrc, characteristic_path);
+	if (!chrc)
+		return btd_error_agent_not_available(msg);
+
+
+	client_device = btd_adapter_find_device_by_path(database->adapter,
+												 client_path);
+	if (!client_device)
+		return btd_error_does_not_exist(msg);
+
+	client_state = find_device_state(database,
+								device_get_address(client_device),
+								btd_device_get_bdaddr_type(client_device));
+	if (!client_state)
+		return btd_error_does_not_exist(msg);
+
+
+	notify.handle = gatt_db_attribute_get_handle(chrc->attrib);
+	notify.ccc_handle = gatt_db_attribute_get_handle(chrc->ccc);
+	notify.database = database;
+	notify.value = value;
+	notify.len = value_len;
+	notify.conf = conf_cb;
+
+	send_notification_to_device(client_state, &notify);
+	DBG("Notification/Indication sent to %s.", client_path);
+	return dbus_message_new_method_return(msg);
+}
+
 static const GDBusMethodTable manager_methods[] = {
 	{ GDBUS_ASYNC_METHOD("RegisterApplication",
 					GDBUS_ARGS({ "application", "o" },
@@ -3623,6 +3710,12 @@  static const GDBusMethodTable manager_methods[] = {
 	{ GDBUS_ASYNC_METHOD("UnregisterApplication",
 					GDBUS_ARGS({ "application", "o" }),
 					NULL, manager_unregister_app) },
+	{ GDBUS_ASYNC_METHOD("NotifyCharacteristicChanged",
+					GDBUS_ARGS({"application", "o" },
+					{ "device", "o" },
+					{ "characteristic_path", "o"},
+					{ "value", "ay"}),
+					NULL, notify_characteristic_changed) },
 	{ }
 };