From patchwork Fri Jul 17 19:15:11 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Luiz Augusto von Dentz X-Patchwork-Id: 11671147 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 5750E13B1 for ; Fri, 17 Jul 2020 19:15:19 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 2C1812064C for ; Fri, 17 Jul 2020 19:15:19 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="GCvz0vrA" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1728182AbgGQTPS (ORCPT ); Fri, 17 Jul 2020 15:15:18 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:60234 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1728103AbgGQTPS (ORCPT ); Fri, 17 Jul 2020 15:15:18 -0400 Received: from mail-pj1-x1041.google.com (mail-pj1-x1041.google.com [IPv6:2607:f8b0:4864:20::1041]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 5091AC0619D2 for ; Fri, 17 Jul 2020 12:15:18 -0700 (PDT) Received: by mail-pj1-x1041.google.com with SMTP id ch3so6979603pjb.5 for ; Fri, 17 Jul 2020 12:15:18 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:mime-version :content-transfer-encoding; bh=ofcSy59ESp8nBAyKdvQXxbumDxZMg6HeTOxTvE1Riuw=; b=GCvz0vrAe6peAes71/uhyAz4RxWuVIZ6EJVpFx1bpx0QH2ajnjswhEyEPoXFUROncO UWERIRfXVaF6ccdX/rGWLNkrQcgB+JpvTofCeVzF0gyIQ4BQoX+7oDV0sCeGUHYpDfeE 6g2Bus9RC30tromji8Fb39/GiCBm2DFY17leGo6DqH70X/nHfGXb1L8SNfxeO1SkWcEs zdidIoZEXKmWBOEI/dxiA/lX22eMeGiytVTUhCbx3TeSZwDMB6hHVA8NMLhVZ3f3zjJn UyYR7KhvPSkgVM6wDGVNRRA4xdpmP7MEjUJ3d8z9IdzOlKPryvkkMXbaVmm8yfEfa6eX VScg== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:mime-version :content-transfer-encoding; bh=ofcSy59ESp8nBAyKdvQXxbumDxZMg6HeTOxTvE1Riuw=; b=NC8QU44RbwaMKqQ6QeVHi0z27Hc3douw+YOLFSSruinVvsfy4SHgBxtJbvDfB1/E27 KNr7ghIv0bHYI+4NP05XLC486QoALZtZ5SsFfBYDtJXgSCf0/ZRTUOa020N/6lTDh9xr /qMwbpA8XebZoNLmdrQzz/s9B1WyqLvJpQRIlQWTPx9ghIJYKSUB0CwqaA0dQXt3VHRo 5i4PKYn62jXz1bvQgq7W2xiJjyVTXFWx5BeODO8jiPjQbq//xawRLRKZ+WXV0Lsz12sj kXW8U+Bgn3uPv13QY07QOQWyACXkhAI7B5KiDx08c3wwMxylWwKW7ElepVfikAM7Ft4s zBrQ== X-Gm-Message-State: AOAM530ooA14wO0dk35Z4H9rYtUemUTCAxLlfVKBjDGAFXaMbg2Hutk5 KtViNnx7AP/pAM2Ue58zTnvW893A/qI= X-Google-Smtp-Source: ABdhPJx/sGMBavpUlFB5fLaeOBrNdy3bilHEaO8dnIRw/UVQ6yaIX0A2p++GJWZjpEIRchuDrszixw== X-Received: by 2002:a17:90a:cc03:: with SMTP id b3mr10444585pju.80.1595013317189; Fri, 17 Jul 2020 12:15:17 -0700 (PDT) Received: from localhost.localdomain (c-71-56-157-77.hsd1.or.comcast.net. [71.56.157.77]) by smtp.gmail.com with ESMTPSA id p9sm6488334pgc.77.2020.07.17.12.15.16 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 17 Jul 2020 12:15:16 -0700 (PDT) From: Luiz Augusto von Dentz To: linux-bluetooth@vger.kernel.org Subject: [PATCH BlueZ 1/5] shared/att: Fix possible crash on disconnect Date: Fri, 17 Jul 2020 12:15:11 -0700 Message-Id: <20200717191515.220621-1-luiz.dentz@gmail.com> X-Mailer: git-send-email 2.26.2 MIME-Version: 1.0 Sender: linux-bluetooth-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-bluetooth@vger.kernel.org From: Luiz Augusto von Dentz If there are pending request while disconnecting they would be notified but clients may endup being freed in the proccess which will then be calling bt_att_cancel to cancal its requests causing the following trace: Invalid read of size 4 at 0x1D894C: enable_ccc_callback (gatt-client.c:1627) by 0x1D247B: disc_att_send_op (att.c:417) by 0x1CCC17: queue_remove_all (queue.c:354) by 0x1D47B7: disconnect_cb (att.c:635) by 0x1E0707: watch_callback (io-glib.c:170) by 0x48E963B: g_main_context_dispatch (in /usr/lib/libglib-2.0.so.0.6400.4) by 0x48E9AC7: ??? (in /usr/lib/libglib-2.0.so.0.6400.4) by 0x48E9ECF: g_main_loop_run (in /usr/lib/libglib-2.0.so.0.6400.4) by 0x1E0E97: mainloop_run (mainloop-glib.c:79) by 0x1E13B3: mainloop_run_with_signal (mainloop-notify.c:201) by 0x12BC3B: main (main.c:770) Address 0x7d40a28 is 24 bytes inside a block of size 32 free'd at 0x484A2E0: free (vg_replace_malloc.c:540) by 0x1CCC17: queue_remove_all (queue.c:354) by 0x1CCC83: queue_destroy (queue.c:73) by 0x1D7DD7: bt_gatt_client_free (gatt-client.c:2209) by 0x16497B: batt_free (battery.c:77) by 0x16497B: batt_remove (battery.c:286) by 0x1A0013: service_remove (service.c:176) by 0x1A9B7B: device_remove_gatt_service (device.c:3691) by 0x1A9B7B: gatt_service_removed (device.c:3805) by 0x1CC90B: queue_foreach (queue.c:220) by 0x1DE27B: notify_service_changed.isra.0.part.0 (gatt-db.c:369) by 0x1DE387: notify_service_changed (gatt-db.c:361) by 0x1DE387: gatt_db_service_destroy (gatt-db.c:385) by 0x1DE3EF: gatt_db_remove_service (gatt-db.c:519) by 0x1D674F: discovery_op_complete (gatt-client.c:388) by 0x1D6877: discover_primary_cb (gatt-client.c:1260) by 0x1E220B: discovery_op_complete (gatt-helpers.c:628) by 0x1E249B: read_by_grp_type_cb (gatt-helpers.c:730) by 0x1D247B: disc_att_send_op (att.c:417) by 0x1CCC17: queue_remove_all (queue.c:354) by 0x1D47B7: disconnect_cb (att.c:635) --- src/shared/att.c | 46 ++++++++++++++++++++++++++++++++++++++++------ 1 file changed, 40 insertions(+), 6 deletions(-) diff --git a/src/shared/att.c b/src/shared/att.c index ed3af2920..58f23dfcb 100644 --- a/src/shared/att.c +++ b/src/shared/att.c @@ -84,6 +84,7 @@ struct bt_att { struct queue *req_queue; /* Queued ATT protocol requests */ struct queue *ind_queue; /* Queued ATT protocol indications */ struct queue *write_queue; /* Queue of PDUs ready to send */ + bool in_disc; /* Cleanup queues on disconnect_cb */ bt_att_timeout_func_t timeout_callback; bt_att_destroy_func_t timeout_destroy; @@ -222,8 +223,10 @@ static void destroy_att_send_op(void *data) free(op); } -static void cancel_att_send_op(struct att_send_op *op) +static void cancel_att_send_op(void *data) { + struct att_send_op *op = data; + if (op->destroy) op->destroy(op->user_data); @@ -631,11 +634,6 @@ static bool disconnect_cb(struct io *io, void *user_data) /* Dettach channel */ queue_remove(att->chans, chan); - /* Notify request callbacks */ - queue_remove_all(att->req_queue, NULL, NULL, disc_att_send_op); - queue_remove_all(att->ind_queue, NULL, NULL, disc_att_send_op); - queue_remove_all(att->write_queue, NULL, NULL, disc_att_send_op); - if (chan->pending_req) { disc_att_send_op(chan->pending_req); chan->pending_req = NULL; @@ -654,6 +652,15 @@ static bool disconnect_cb(struct io *io, void *user_data) bt_att_ref(att); + att->in_disc = true; + + /* Notify request callbacks */ + queue_remove_all(att->req_queue, NULL, NULL, disc_att_send_op); + queue_remove_all(att->ind_queue, NULL, NULL, disc_att_send_op); + queue_remove_all(att->write_queue, NULL, NULL, disc_att_send_op); + + att->in_disc = false; + queue_foreach(att->disconn_list, disconn_handler, INT_TO_PTR(err)); bt_att_unregister_all(att); @@ -1574,6 +1581,30 @@ bool bt_att_chan_cancel(struct bt_att_chan *chan, unsigned int id) return true; } +static bool bt_att_disc_cancel(struct bt_att *att, unsigned int id) +{ + struct att_send_op *op; + + op = queue_find(att->req_queue, match_op_id, UINT_TO_PTR(id)); + if (op) + goto done; + + op = queue_find(att->ind_queue, match_op_id, UINT_TO_PTR(id)); + if (op) + goto done; + + op = queue_find(att->write_queue, match_op_id, UINT_TO_PTR(id)); + +done: + if (!op) + return false; + + /* Just cancel since disconnect_cb will be cleaning up */ + cancel_att_send_op(op); + + return true; +} + bool bt_att_cancel(struct bt_att *att, unsigned int id) { const struct queue_entry *entry; @@ -1591,6 +1622,9 @@ bool bt_att_cancel(struct bt_att *att, unsigned int id) return true; } + if (att->in_disc) + return bt_att_disc_cancel(att, id); + op = queue_remove_if(att->req_queue, match_op_id, UINT_TO_PTR(id)); if (op) goto done; From patchwork Fri Jul 17 19:15:12 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Luiz Augusto von Dentz X-Patchwork-Id: 11671151 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 7EDF713B1 for ; Fri, 17 Jul 2020 19:15:21 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 670982064C for ; Fri, 17 Jul 2020 19:15:21 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="iub5c/00" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1728238AbgGQTPV (ORCPT ); Fri, 17 Jul 2020 15:15:21 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:60244 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1728202AbgGQTPU (ORCPT ); Fri, 17 Jul 2020 15:15:20 -0400 Received: from mail-pj1-x1044.google.com (mail-pj1-x1044.google.com [IPv6:2607:f8b0:4864:20::1044]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 8AE26C0619D2 for ; Fri, 17 Jul 2020 12:15:20 -0700 (PDT) Received: by mail-pj1-x1044.google.com with SMTP id gc9so6980696pjb.2 for ; Fri, 17 Jul 2020 12:15:20 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=gNYmXc4mJEmOu5CETp29vjI9I1CoKaM9O5sbDcmH11I=; b=iub5c/007xX6B3c843zs99TwrWVioltW41PZQX6AbfGcdi6SgxY120mV5CDc++qhbk yTszbsp6O675hDh5kYegPxk/7W3h1XEnTSD/0Q9yspPWFDxC4W2TGrbpXVM6pthuNIoW V7Tl5s6Zck3RlEfEHyovFt6dqlOpTNEnLyH6qUGpuhPrf2ebE28SfILLvzVUZ5Zq06n3 /cvRUsKw4rJL7d18zfmT9podkQUh4NnsJ8MzRb79nAP4m7W33AIEtdXp9/PjAl9MKs9H weOvCM8/yGxZcbyNfdW9mNRrs9wMgvwwRrrdxHDzGOJ17B9+jjDhIcFTVlsvooskUrHj EMGQ== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=gNYmXc4mJEmOu5CETp29vjI9I1CoKaM9O5sbDcmH11I=; b=VK3iwBd6SIQ5uUaJO1cChZUJxQj1SMcUe8zrg8qwzVHGGLrOPq4pKeZlkM0czFn8G7 1OqkPzfHm1wfcCd2HAIKMdnNrVOvTfu3kBXHbYbeXyRuiwFN5zRbOLyMyaM2THTtmy6d hK4JGvCbUpSUlC22zEkvPjJdOliptNSfYY1hMVKpdY8m6+NFCKllryctiv0XPLYy4WIM XWM9DtqgOSDaePHkaSvyZkzVnV0d9yAHcPVp7NdEO/jWW3o/vRoKZA2ozWr9xkr268oC o/gtFlenCxzqA8iVnYAJw4KzewHBT5adbJ1xyl4Q53uRLTSrmmO5DC7pH5EkgeTMIg9X SpwA== X-Gm-Message-State: AOAM532XGCqAbe6XvldFvdh9HpZAdkO4G/R83HKBhuvN/OHivDQNJ+MD 2lEYYMqCx1JExDQ9fr/ai1lIOm79WM0= X-Google-Smtp-Source: ABdhPJwAbT2zm+o2JO3CRnlgp9Dtf7KOk/A2akVkwzWFCw3/VVSf9NxriJUqRCRFxwtUbjAlinwPoA== X-Received: by 2002:a17:90a:a783:: with SMTP id f3mr11466177pjq.142.1595013318353; Fri, 17 Jul 2020 12:15:18 -0700 (PDT) Received: from localhost.localdomain (c-71-56-157-77.hsd1.or.comcast.net. [71.56.157.77]) by smtp.gmail.com with ESMTPSA id p9sm6488334pgc.77.2020.07.17.12.15.17 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 17 Jul 2020 12:15:17 -0700 (PDT) From: Luiz Augusto von Dentz To: linux-bluetooth@vger.kernel.org Subject: [PATCH BlueZ 2/5] shared/gatt-db: Add support for notifying attribute changes Date: Fri, 17 Jul 2020 12:15:12 -0700 Message-Id: <20200717191515.220621-2-luiz.dentz@gmail.com> X-Mailer: git-send-email 2.26.2 In-Reply-To: <20200717191515.220621-1-luiz.dentz@gmail.com> References: <20200717191515.220621-1-luiz.dentz@gmail.com> MIME-Version: 1.0 Sender: linux-bluetooth-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-bluetooth@vger.kernel.org From: Luiz Augusto von Dentz This enables to get notified when an attribute has been changed e.g. it is being removed so the code can detect changes changes at attribute level. --- src/shared/gatt-db.c | 103 +++++++++++++++++++++++++++++++++++++++++++ src/shared/gatt-db.h | 8 ++++ 2 files changed, 111 insertions(+) diff --git a/src/shared/gatt-db.c b/src/shared/gatt-db.c index 5eccab3b9..e939ddc3a 100644 --- a/src/shared/gatt-db.c +++ b/src/shared/gatt-db.c @@ -81,6 +81,13 @@ struct notify { void *user_data; }; +struct attribute_notify { + unsigned int id; + gatt_db_attribute_cb_t removed; + gatt_db_destroy_func_t destroy; + void *user_data; +}; + struct pending_read { struct gatt_db_attribute *attrib; unsigned int id; @@ -114,6 +121,9 @@ struct gatt_db_attribute { unsigned int write_id; struct queue *pending_writes; + + unsigned int next_notify_id; + struct queue *notify_list; }; struct gatt_db_service { @@ -171,6 +181,16 @@ static void pending_write_free(void *data) pending_write_result(p, -ECANCELED); } +static void attribute_notify_destroy(void *data) +{ + struct attribute_notify *notify = data; + + if (notify->destroy) + notify->destroy(notify->user_data); + + free(notify); +} + static void attribute_destroy(struct gatt_db_attribute *attribute) { /* Attribute was not initialized by user */ @@ -179,6 +199,7 @@ static void attribute_destroy(struct gatt_db_attribute *attribute) queue_destroy(attribute->pending_reads, pending_read_free); queue_destroy(attribute->pending_writes, pending_write_free); + queue_destroy(attribute->notify_list, attribute_notify_destroy); free(attribute->value); free(attribute); @@ -208,6 +229,7 @@ static struct gatt_db_attribute *new_attribute(struct gatt_db_service *service, attribute->pending_reads = queue_new(); attribute->pending_writes = queue_new(); + attribute->notify_list = queue_new(); return attribute; @@ -352,12 +374,38 @@ static bool db_hash_update(void *user_data) return false; } +static void handle_attribute_notify(void *data, void *user_data) +{ + struct attribute_notify *notify = data; + struct gatt_db_attribute *attrib = user_data; + + if (notify->removed) + notify->removed(attrib, notify->user_data); +} + +static void notify_attribute_changed(struct gatt_db_service *service) +{ + int i; + + for (i = 0; i < service->num_handles; i++) { + struct gatt_db_attribute *attr = service->attributes[i]; + + if (!attr) + continue; + + queue_foreach(attr->notify_list, handle_attribute_notify, attr); + } +} + static void notify_service_changed(struct gatt_db *db, struct gatt_db_service *service, bool added) { struct notify_data data; + if (!added) + notify_attribute_changed(service); + if (queue_isempty(db->notify_list)) return; @@ -1993,3 +2041,58 @@ void *gatt_db_attribute_get_user_data(struct gatt_db_attribute *attrib) return attrib->user_data; } + +static bool match_attribute_notify_id(const void *a, const void *b) +{ + const struct attribute_notify *notify = a; + unsigned int id = PTR_TO_UINT(b); + + return notify->id == id; +} + +unsigned int gatt_db_attribute_register(struct gatt_db_attribute *attrib, + gatt_db_attribute_cb_t removed, + void *user_data, + gatt_db_destroy_func_t destroy) +{ + struct attribute_notify *notify; + + if (!attrib || !removed) + return 0; + + notify = new0(struct attribute_notify, 1); + notify->removed = removed; + notify->destroy = destroy; + notify->user_data = user_data; + + if (attrib->next_notify_id < 1) + attrib->next_notify_id = 1; + + notify->id = attrib->next_notify_id++; + + if (!queue_push_tail(attrib->notify_list, notify)) { + free(notify); + return 0; + } + + return notify->id; +} + +bool gatt_db_attribute_unregister(struct gatt_db_attribute *attrib, + unsigned int id) +{ + struct attribute_notify *notify; + + if (!attrib || !id) + return false; + + notify = queue_find(attrib->notify_list, match_attribute_notify_id, + UINT_TO_PTR(id)); + if (!notify) + return false; + + queue_remove(attrib->notify_list, notify); + attribute_notify_destroy(notify); + + return true; +} diff --git a/src/shared/gatt-db.h b/src/shared/gatt-db.h index a0fd66c53..5bf19d302 100644 --- a/src/shared/gatt-db.h +++ b/src/shared/gatt-db.h @@ -281,3 +281,11 @@ bool gatt_db_attribute_write_result(struct gatt_db_attribute *attrib, bool gatt_db_attribute_reset(struct gatt_db_attribute *attrib); void *gatt_db_attribute_get_user_data(struct gatt_db_attribute *attrib); + +unsigned int gatt_db_attribute_register(struct gatt_db_attribute *attrib, + gatt_db_attribute_cb_t removed, + void *user_data, + gatt_db_destroy_func_t destroy); + +bool gatt_db_attribute_unregister(struct gatt_db_attribute *attrib, + unsigned int id); From patchwork Fri Jul 17 19:15:13 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Luiz Augusto von Dentz X-Patchwork-Id: 11671149 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 3187513A4 for ; Fri, 17 Jul 2020 19:15:21 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 1A89B2076D for ; Fri, 17 Jul 2020 19:15:21 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="dC81Zl+9" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1728209AbgGQTPU (ORCPT ); Fri, 17 Jul 2020 15:15:20 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:60242 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1728103AbgGQTPU (ORCPT ); Fri, 17 Jul 2020 15:15:20 -0400 Received: from mail-pf1-x430.google.com (mail-pf1-x430.google.com [IPv6:2607:f8b0:4864:20::430]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 1FB3BC0619D2 for ; Fri, 17 Jul 2020 12:15:20 -0700 (PDT) Received: by mail-pf1-x430.google.com with SMTP id 207so5860653pfu.3 for ; Fri, 17 Jul 2020 12:15:20 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=Q9H7Dmvj+o5rqZS7a9SM6wIi9VBpMGGwPN+3ZrU8m10=; b=dC81Zl+9VTGrL7AkP6HTC9WEGMwXKRb3Vj+ck/pu4M0S47xj8/fJap9oC8/vjC+cAz zA5B/2lQvOekItjKUy3r8YqjVQ1eW/BbWw21Q/y0VEiJY6wYMxUwOwmgbpTcTY+5c25T qMKAMHkK10rJU6BGjZqXtV8KvUNV5Qrd6/5/Ntd1WgaGK5hV4mH4lCUol4wHfX3aGHPb khLWjnDvmnp70FevaNX8kzEh9QWZjP95fLJoE0Inr1uTMVhuLCLNwZ7O2JiUov6fpBKp lF85udH9yhxBuEeGuI5/dKMJcfqqAn62DA8KLvCDY+ud3Ni8Atp32U1gA4b46mnzktY3 Liaw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=Q9H7Dmvj+o5rqZS7a9SM6wIi9VBpMGGwPN+3ZrU8m10=; b=ojgHF7Pi1mrjdMp/IuDq6r4DguqRTPoH8p3Oc8DvLU99b3suASI7t3mikjJ+Q/wH1W wuw86rJ9qjWvbqLJDm9mVb/xM6EyZp/qspixWrPoTMYD1fSS2PZugqtrhaW0xlsvnfAu If7rjVON1RxoB3ADW/1WRTLyQ/TJacj+moQS3wrw/Yzo4od6dfMgVSrml/Ysz8d5DpzF 0hXIjL0JF6DIuqKDbuHrPmv+67KB/fdw3dXyLeguas4DUU5b/LR/z4W5jNJ9vWcUc1aF 6LhoguPghMer20HTGXS7LYT6f7wEuI75wpazBuPftK19QepmbcKH7RARwfTJr3G8cr3O WGdw== X-Gm-Message-State: AOAM530BYbyfDIrEifBlz8STNgcqYnQKqQEuEty8Qlph3vF8gl3egoyf G6iXPzwea7Y4Mbjpe5jkXKDVinNpLAA= X-Google-Smtp-Source: ABdhPJybdTArBWSGRRs9r2Rw2wXC9SD26Xnp4l2efKvY4Yc4Ffmq2sWO3feUcW/6HCiBWKutTbBbxQ== X-Received: by 2002:a05:6a00:84e:: with SMTP id q14mr9299793pfk.309.1595013319293; Fri, 17 Jul 2020 12:15:19 -0700 (PDT) Received: from localhost.localdomain (c-71-56-157-77.hsd1.or.comcast.net. [71.56.157.77]) by smtp.gmail.com with ESMTPSA id p9sm6488334pgc.77.2020.07.17.12.15.18 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 17 Jul 2020 12:15:18 -0700 (PDT) From: Luiz Augusto von Dentz To: linux-bluetooth@vger.kernel.org Subject: [PATCH BlueZ 3/5] shared/gatt-client: Remove notification if its attribute is removed Date: Fri, 17 Jul 2020 12:15:13 -0700 Message-Id: <20200717191515.220621-3-luiz.dentz@gmail.com> X-Mailer: git-send-email 2.26.2 In-Reply-To: <20200717191515.220621-1-luiz.dentz@gmail.com> References: <20200717191515.220621-1-luiz.dentz@gmail.com> MIME-Version: 1.0 Sender: linux-bluetooth-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-bluetooth@vger.kernel.org From: Luiz Augusto von Dentz If the attribute is being removed from the database it means the notification shall also be dropped, that way users don't have to cleanup its subscriptions themselves. --- src/shared/gatt-client.c | 70 +++++++++++++++++++++++++++++----------- 1 file changed, 52 insertions(+), 18 deletions(-) diff --git a/src/shared/gatt-client.c b/src/shared/gatt-client.c index 0b81a7a5c..e21aca1f0 100644 --- a/src/shared/gatt-client.c +++ b/src/shared/gatt-client.c @@ -174,9 +174,12 @@ static void request_unref(void *data) } struct notify_chrc { + struct bt_gatt_client *client; + struct gatt_db_attribute *attr; uint16_t value_handle; uint16_t ccc_handle; uint16_t properties; + unsigned int notify_id; int notify_count; /* Reference count of registered notify callbacks */ /* Pending calls to register_notify are queued here so that they can be @@ -235,6 +238,51 @@ static void find_ccc(struct gatt_db_attribute *attr, void *user_data) *ccc_ptr = attr; } +static bool match_notify_chrc(const void *data, const void *user_data) +{ + const struct notify_data *notify_data = data; + const struct notify_chrc *chrc = user_data; + + return notify_data->chrc == chrc; +} + +static void notify_data_cleanup(void *data) +{ + struct notify_data *notify_data = data; + + if (notify_data->att_id) + bt_att_cancel(notify_data->client->att, notify_data->att_id); + + notify_data_unref(notify_data); +} + +static void notify_chrc_free(void *data) +{ + struct notify_chrc *chrc = data; + + if (chrc->notify_id) + gatt_db_attribute_unregister(chrc->attr, chrc->notify_id); + + queue_destroy(chrc->reg_notify_queue, notify_data_unref); + free(chrc); +} + +static void chrc_removed(struct gatt_db_attribute *attr, void *user_data) +{ + struct notify_chrc *chrc = user_data; + struct bt_gatt_client *client = chrc->client; + struct notify_data *data; + + chrc->notify_id = 0; + + while ((data = queue_remove_if(client->notify_list, match_notify_chrc, + chrc))) + notify_data_cleanup(data); + + queue_remove(client->notify_chrcs, chrc); + notify_chrc_free(chrc); +} + static struct notify_chrc *notify_chrc_create(struct bt_gatt_client *client, uint16_t value_handle) { @@ -274,22 +322,18 @@ static struct notify_chrc *notify_chrc_create(struct bt_gatt_client *client, if (ccc) chrc->ccc_handle = gatt_db_attribute_get_handle(ccc); + chrc->client = client; + chrc->attr = attr; chrc->value_handle = value_handle; chrc->properties = properties; + chrc->notify_id = gatt_db_attribute_register(attr, chrc_removed, chrc, + NULL); queue_push_tail(client->notify_chrcs, chrc); return chrc; } -static void notify_chrc_free(void *data) -{ - struct notify_chrc *chrc = data; - - queue_destroy(chrc->reg_notify_queue, notify_data_unref); - free(chrc); -} - static bool match_notify_data_id(const void *a, const void *b) { const struct notify_data *notify_data = a; @@ -303,16 +347,6 @@ struct handle_range { uint16_t end; }; -static void notify_data_cleanup(void *data) -{ - struct notify_data *notify_data = data; - - if (notify_data->att_id) - bt_att_cancel(notify_data->client->att, notify_data->att_id); - - notify_data_unref(notify_data); -} - struct discovery_op; typedef void (*discovery_op_complete_func_t)(struct discovery_op *op, From patchwork Fri Jul 17 19:15:14 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Luiz Augusto von Dentz X-Patchwork-Id: 11671153 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 6962413B1 for ; Fri, 17 Jul 2020 19:15:22 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 50D142064C for ; Fri, 17 Jul 2020 19:15:22 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="plKj0A5+" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1728312AbgGQTPV (ORCPT ); Fri, 17 Jul 2020 15:15:21 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:60246 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1728202AbgGQTPV (ORCPT ); Fri, 17 Jul 2020 15:15:21 -0400 Received: from mail-pj1-x1036.google.com (mail-pj1-x1036.google.com [IPv6:2607:f8b0:4864:20::1036]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 05D38C0619D2 for ; Fri, 17 Jul 2020 12:15:21 -0700 (PDT) Received: by mail-pj1-x1036.google.com with SMTP id md7so6852863pjb.1 for ; Fri, 17 Jul 2020 12:15:21 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=ATkHjHvmlTIlEcbg7ocsMTKN2/DIf8EdCBGX5pPpsu0=; b=plKj0A5+0+pIQ5vMicUPmk9ttxFrwTUGYF8Xu/pS1rQl5/Og4uvrMV4/pUyatNu/Rm w9++F9MlP4p48IqyQqDmFZS590VNPq97qfr39iwycqZEFEI0uAvRBOMjLqy+nE9mfJ4P a80Nw/3OA1L2J8DZwNnbq+JbC807pZfCt06ljRP7xo33S9BSO4Zyze9pNdUBtoGSRUuC ooNn5aQq2V3Qv8KmzB9OVA/Vcs2IkP/AtdhhBV/Q0Y6wHVk1vhBPo/W8SBhPuWrUUFOV Q5SR1tksMlKdZXEJQs7HGAgwCWO+yPEna1o5LHJJMXueYMhxDDO+u4ZP0ebNSDlMrqAo taLQ== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=ATkHjHvmlTIlEcbg7ocsMTKN2/DIf8EdCBGX5pPpsu0=; b=SPRZUQWElscndWwOSiOBfal+AoYUez2UcywOrRJ3onjYceVF6Ue4BllhZOpHqM+TDr Y4AH3GtVa2FAi5RCPynVoHLfcf0P/P+s9dB47Zc4f263TGRf1OdiExgAUXt8XnpLBsr4 6bme2a/7gQDKhTHRZhEFtKZQ1NmNbhJMCCkNQtyup2EFRIsny5nULDuFCArDQ75HFpzt EVRvu/N1flYVSs9FX0sn/KJGWwG+7I6DnTrGsXAMmTsbyVbVAMg/uAQcY6pYfq68U5Ft h6BCDQz3Epe5D5MJIxX9nCN2xHyvvctYOluAt1XnBcz5IPx5kpllyOBv6jrkmEr0n8wG deAQ== X-Gm-Message-State: AOAM532dl0mcT4Ajdn8/NE/7bxsMy5EB8GNzRN9YSTyf2VCNshRgdrbx 53pNLeLxUhMFoTkeOSI9bNR+Uj2EWn4= X-Google-Smtp-Source: ABdhPJyw49NmFaXrDTbQS4uSKs61ZibUHgBozKcj+P/SioV7SyLcuo36bh7yxaTEioXdaj5xl0c+Sw== X-Received: by 2002:a17:90a:c28f:: with SMTP id f15mr11555127pjt.72.1595013320253; Fri, 17 Jul 2020 12:15:20 -0700 (PDT) Received: from localhost.localdomain (c-71-56-157-77.hsd1.or.comcast.net. [71.56.157.77]) by smtp.gmail.com with ESMTPSA id p9sm6488334pgc.77.2020.07.17.12.15.19 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 17 Jul 2020 12:15:19 -0700 (PDT) From: Luiz Augusto von Dentz To: linux-bluetooth@vger.kernel.org Subject: [PATCH BlueZ 4/5] shared/gatt-client: Don't remove active services Date: Fri, 17 Jul 2020 12:15:14 -0700 Message-Id: <20200717191515.220621-4-luiz.dentz@gmail.com> X-Mailer: git-send-email 2.26.2 In-Reply-To: <20200717191515.220621-1-luiz.dentz@gmail.com> References: <20200717191515.220621-1-luiz.dentz@gmail.com> MIME-Version: 1.0 Sender: linux-bluetooth-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-bluetooth@vger.kernel.org From: Luiz Augusto von Dentz If discovery was aborted (i.e due to a disconnect) check if pending services were active so only staled services which were not completed fetched are removed. --- src/shared/gatt-client.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/shared/gatt-client.c b/src/shared/gatt-client.c index e21aca1f0..409a3ee57 100644 --- a/src/shared/gatt-client.c +++ b/src/shared/gatt-client.c @@ -412,6 +412,10 @@ static void discovery_op_complete(struct discovery_op *op, bool success, struct gatt_db_attribute *attr = svc->data; uint16_t start, end; + /* Leave active services if operation was aborted */ + if ((!success && err == 0) && gatt_db_service_get_active(attr)) + continue; + gatt_db_attribute_get_service_data(attr, &start, &end, NULL, NULL); From patchwork Fri Jul 17 19:15:15 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Luiz Augusto von Dentz X-Patchwork-Id: 11671155 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id EEEE014E3 for ; Fri, 17 Jul 2020 19:15:22 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id D8B862076D for ; Fri, 17 Jul 2020 19:15:22 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="QEzvugMW" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1728346AbgGQTPW (ORCPT ); Fri, 17 Jul 2020 15:15:22 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:60252 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1728202AbgGQTPV (ORCPT ); Fri, 17 Jul 2020 15:15:21 -0400 Received: from mail-pg1-x542.google.com (mail-pg1-x542.google.com [IPv6:2607:f8b0:4864:20::542]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id DEE81C0619D2 for ; Fri, 17 Jul 2020 12:15:21 -0700 (PDT) Received: by mail-pg1-x542.google.com with SMTP id z5so7137182pgb.6 for ; Fri, 17 Jul 2020 12:15:21 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=9CGEiPF9wLML97aLDtUYlsZfnzcMXSIYdV6ccazgttk=; b=QEzvugMW3rA8H/hC61bH5KXTPgjAxuP1722fOdVyFEjhHCc4GzcHWSIC93EOC3LuZi r6we0pvaCPKQZXKcL6NVsRecO4MDz2Zy+thz1nf9HdF3AR5egnBmyTrCoJ57LtuwzzX2 6LYK727UJVvCxOMnjB0GMhXbpf3qNleD9pDyaiF5S8yPzgh7DJgVdR0BVrlQ6IF2A3mg qGTfjaJpaTsB3BqZq2aEdAMz/kQOM9xAXEnxxyTcTwVXc0XWa8ZMnmzCFMG0JLNdPyt1 V3Us5Jo1t2Rw7TRaY6aDvVNpIb7Wehvctt0l4stjs7wvvymnCvC1P0sSFZraqFu0X990 KfWw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=9CGEiPF9wLML97aLDtUYlsZfnzcMXSIYdV6ccazgttk=; b=T2X0JcmbMwpCLIOP1DSMG2XwlIvt3sQp5TazGca/ePyM5zPWMpWwQzYS+dT/AoQv+0 TBsGKra9xGQcJTABm3A5dV03hTwct8yhMHC9RFvqTDZwWJ65cGdfCs7LULGA2I4KZgt1 ex5RmyVDj7k6MEh7rfBmWk/EZwy727doATvyNrschYKev33PB/AmuprLjqhe2CVF8dH1 DPnkT/0C/LCGcnhzfi4d1c8IVtymrwH+pl2dnXmWkqKC2mqjx5CdNpPR4QHDO/j1Kesx WE/sw2XQds1QswIY3DmlXpDPYRQ9B34iwgguTyaX5QL+E6PLGnQtEH999JgjFjLp/mxx joZA== X-Gm-Message-State: AOAM533GXqM1AnZQwXbmWckMosNXXrpaIFwFPBnJ5iHbQ55HBaji0e1Y cilIkIizSLXgvgK+449Kfp3G//3MDcc= X-Google-Smtp-Source: ABdhPJxE/kSuEPzqBxwJlkkjCaqfKc/JiIsh92nF0YkFH7s8pgVSHeKGGpieTucKHVjYaJBDueSXCw== X-Received: by 2002:a05:6a00:78a:: with SMTP id g10mr9473873pfu.0.1595013321219; Fri, 17 Jul 2020 12:15:21 -0700 (PDT) Received: from localhost.localdomain (c-71-56-157-77.hsd1.or.comcast.net. [71.56.157.77]) by smtp.gmail.com with ESMTPSA id p9sm6488334pgc.77.2020.07.17.12.15.20 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 17 Jul 2020 12:15:20 -0700 (PDT) From: Luiz Augusto von Dentz To: linux-bluetooth@vger.kernel.org Subject: [PATCH BlueZ 5/5] shared/gatt-client: Fix handling of service changed Date: Fri, 17 Jul 2020 12:15:15 -0700 Message-Id: <20200717191515.220621-5-luiz.dentz@gmail.com> X-Mailer: git-send-email 2.26.2 In-Reply-To: <20200717191515.220621-1-luiz.dentz@gmail.com> References: <20200717191515.220621-1-luiz.dentz@gmail.com> MIME-Version: 1.0 Sender: linux-bluetooth-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-bluetooth@vger.kernel.org From: Luiz Augusto von Dentz When handling multiple service changed multiple discovery operations would be performed but at the end of each one the hash would be read which not only would create extra traffic but also prevents the code to properly detection services disappering. --- src/shared/gatt-client.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/src/shared/gatt-client.c b/src/shared/gatt-client.c index 409a3ee57..f6cff5014 100644 --- a/src/shared/gatt-client.c +++ b/src/shared/gatt-client.c @@ -1460,8 +1460,10 @@ static bool read_db_hash(struct discovery_op *op) struct bt_gatt_client *client = op->client; bt_uuid_t uuid; - /* Check if hash was already read */ - if (op->hash) + /* Check if hash was already been read or there are more services to + * process. + */ + if (op->hash || !queue_isempty(client->svc_chngd_queue)) return false; bt_uuid16_create(&uuid, GATT_CHARAC_DB_HASH);