Re: [PATCH] Release references to technologies held by rfkill during cleanup.

2014-10-23 Thread Patrik Flykt
On Tue, 2014-10-21 at 12:31 -0500, David Lechner wrote:
 Bluetooth, however, never sent this signal,

This is caused because there are two plugins for Bluetooth, one for
Bluez 4 and the other one for Bluez 5. Both register a
connman_technology_driver. So far so good.

The problem is caused by technology_get(type) in
__connman_technology_add_rfkill(), with more than one technology driver
this add function is called multiple times, each time increasing the
reference count of the technology by one. It's not that easy to fix, as
the technology is created when there is a technology driver present and
either an rfkill switch or a connman device is added to the system.

While I'm thinking on how to solve this, the UI mopping up after a
sudden ConnMan disappearance from D-Bus looks suddenly like a very good
and easy solution to the initial problem...


Cheers,

Patrik


___
connman mailing list
connman@connman.net
https://lists.connman.net/mailman/listinfo/connman


Re: [PATCH] Release references to technologies held by rfkill during cleanup.

2014-10-23 Thread David Lechner

On 10/23/2014 08:04 AM, Patrik Flykt wrote:
This is caused because there are two plugins for Bluetooth, one for 
Bluez 4 and the other one for Bluez 5. Both register a 
connman_technology_driver. So far so good. The problem is caused by 
technology_get(type) in __connman_technology_add_rfkill(), with more 
than one technology driver this add function is called multiple times, 
each time increasing the reference count of the technology by one. 
It's not that easy to fix, as the technology is created when there is 
a technology driver present and either an rfkill switch or a connman 
device is added to the system. While I'm thinking on how to solve 
this, the UI mopping up after a sudden ConnMan disappearance from 
D-Bus looks suddenly like a very good and easy solution to the initial 
problem...
I see what you mean. I guess the reason my initial patch seemed like it 
works is because there was only one extra technology_get called. If 
there were three Bluetooth drivers, then it would not work.


It seems like you might be able to have an rfkill_get and rfkill_put so 
that the first driver that is registered that calls rfkill_get will call 
__connman_technology_add_rfkill, but subsequent calls to rfkill_get will 
just return without calling __connman_technology_add_rfkill. When the 
last driver is unregistered that calls rfkill_put, then it should in 
turn call __connman_technology_remove_rfkill. Of course, rfkill_process 
in src/rfkill.c would have to be modified to work with this as well.

___
connman mailing list
connman@connman.net
https://lists.connman.net/mailman/listinfo/connman


Re: [PATCH] Release references to technologies held by rfkill during cleanup.

2014-10-22 Thread Patrik Flykt

Hi,

On Tue, 2014-10-21 at 12:27 -0500, David Lechner wrote:
 ---
   src/connman.h|  1 +
   src/rfkill.c |  2 ++
   src/technology.c | 15 +++
   3 files changed, 18 insertions(+)
 
 diff --git a/src/connman.h b/src/connman.h
 index da01215..bab013b 100644
 --- a/src/connman.h
 +++ b/src/connman.h
 @@ -826,6 +826,7 @@ void __connman_service_save(struct connman_service 
 *service);
#include connman/notifier.h
   +void __connman_technology_cleanup_rfkill(void);
   int __connman_technology_init(void);
   void __connman_technology_cleanup(void);
   diff --git a/src/rfkill.c b/src/rfkill.c
 index 960cfea..2f073a9 100644
 --- a/src/rfkill.c
 +++ b/src/rfkill.c
 @@ -232,4 +232,6 @@ void __connman_rfkill_cleanup(void)
   g_io_channel_unref(channel);
   channel = NULL;
 +
 + __connman_technology_cleanup_rfkill();
   }
 diff --git a/src/technology.c b/src/technology.c
 index d80d9e6..5917c59 100644
 --- a/src/technology.c
 +++ b/src/technology.c
 @@ -1776,6 +1776,21 @@ int __connman_technology_remove_rfkill(unsigned 
 int index,
   return 0;
   }
   +gboolean find_first(gpointer key, gpointer value, gpointer user_data)
 +{
 + return TRUE;
 +}
 +
 +void __connman_technology_cleanup_rfkill(void)
 +{
 + struct connman_rfkill *rfkill;
 +
 + DBG();
 +
 + while (rfkill = g_hash_table_find(rfkill_list, find_first, NULL))
 + __connman_technology_remove_rfkill(rfkill-index, rfkill-type);
 +}
 +
   int __connman_technology_init(void)
   {
   DBG();

This sort of works, but I'd like to fix the problem in src/technology.c,
where the problem manifests itself.

So it seems ConnMan is not doing the technology_put() cleanup in the
correct place. As you noticed this currently happens only in
__connman_technology_remove(), and not on shutdown where only
free_rfkill() is called. So the code starting with the line technology
= technology_find(type); in __connman_technology_remove() should
actually happen in free_rfkill() instead. That way no matter what frees
up an rfkill structure also causes a technology_put() where the last one
sends off a TechnologRemoved signal before destroying the technology
structure.

Cheers,

Patrik


___
connman mailing list
connman@connman.net
https://lists.connman.net/mailman/listinfo/connman


Re: [PATCH] Release references to technologies held by rfkill during cleanup.

2014-10-22 Thread David Lechner

On 10/22/2014 03:14 AM, Patrik Flykt wrote:

So it seems ConnMan is not doing the technology_put() cleanup in the
correct place. As you noticed this currently happens only in
__connman_technology_remove(), and not on shutdown where only
free_rfkill() is called. So the code starting with the line technology
= technology_find(type); in __connman_technology_remove() should
actually happen in free_rfkill() instead. That way no matter what frees
up an rfkill structure also causes a technology_put() where the last one
sends off a TechnologRemoved signal before destroying the technology
structure.

I tried this suggestion, but it does not fix the problem I was trying to 
fix. rfkill_list is destroyed in __connman_technology_cleanup which 
happens long after plugins are cleaned up. This means most if not all 
technologies have already been destroyed (possibly without being 
properly released/removed) before we get to this point.


Based on your other reply though, it sounds like I need to fix my UI. I 
did not consider the case of a connman crash, which would be a good 
thing to handle. Also, there is the Released DBus signal that I was 
overlooking.


Here is the patch of what I did to implement your suggestion.

--- connman-1.26.orig/src/technology.c
+++ connman-1.26/src/technology.c
@@ -364,13 +364,6 @@ bool connman_technology_get_wifi_tetheri
 return true;
 }

-static void free_rfkill(gpointer data)
-{
-struct connman_rfkill *rfkill = data;
-
-g_free(rfkill);
-}
-
 static void technology_load(struct connman_technology *technology)
 {
 GKeyFile *keyfile;
@@ -1764,18 +1757,26 @@ int __connman_technology_remove_rfkill(u

 g_hash_table_remove(rfkill_list, GINT_TO_POINTER(index));

-technology = technology_find(type);
-if (!technology)
-return -ENXIO;
+return 0;
+}

-technology_apply_rfkill_change(technology,
-technology-softblocked, !technology-hardblocked, false);
+static void free_rfkill(gpointer data)
+{
+struct connman_rfkill *rfkill = data;
+struct connman_technology *technology;

-technology_put(technology);
+technology = technology_find(rfkill-type);
+if (technology) {
+technology_apply_rfkill_change(technology,
+technology-softblocked, !technology-hardblocked, false);

-return 0;
+technology_put(technology);
+}
+
+g_free(rfkill);
 }

+
 int __connman_technology_init(void)
 {
 DBG();

___
connman mailing list
connman@connman.net
https://lists.connman.net/mailman/listinfo/connman


[PATCH] Release references to technologies held by rfkill during cleanup.

2014-10-21 Thread David Lechner

---
 src/connman.h|  1 +
 src/rfkill.c |  2 ++
 src/technology.c | 15 +++
 3 files changed, 18 insertions(+)

diff --git a/src/connman.h b/src/connman.h
index da01215..bab013b 100644
--- a/src/connman.h
+++ b/src/connman.h
@@ -826,6 +826,7 @@ void __connman_service_save(struct connman_service 
*service);

  #include connman/notifier.h
 +void __connman_technology_cleanup_rfkill(void);
 int __connman_technology_init(void);
 void __connman_technology_cleanup(void);
 diff --git a/src/rfkill.c b/src/rfkill.c
index 960cfea..2f073a9 100644
--- a/src/rfkill.c
+++ b/src/rfkill.c
@@ -232,4 +232,6 @@ void __connman_rfkill_cleanup(void)
g_io_channel_unref(channel);
channel = NULL;
+
+   __connman_technology_cleanup_rfkill();
 }
diff --git a/src/technology.c b/src/technology.c
index d80d9e6..5917c59 100644
--- a/src/technology.c
+++ b/src/technology.c
@@ -1776,6 +1776,21 @@ int __connman_technology_remove_rfkill(unsigned 
int index,

return 0;
 }
 +gboolean find_first(gpointer key, gpointer value, gpointer user_data)
+{
+   return TRUE;
+}
+
+void __connman_technology_cleanup_rfkill(void)
+{
+   struct connman_rfkill *rfkill;
+
+   DBG();
+
+   while (rfkill = g_hash_table_find(rfkill_list, find_first, NULL))
+   __connman_technology_remove_rfkill(rfkill-index, rfkill-type);
+}
+
 int __connman_technology_init(void)
 {
DBG();
--
1.9.1

___
connman mailing list
connman@connman.net
https://lists.connman.net/mailman/listinfo/connman


Re: [PATCH] Release references to technologies held by rfkill during cleanup.

2014-10-21 Thread David Lechner
I have written a UI for connman an ran into an bug when restarting 
connman. When restarting, most technologies send the TechnologyRemoved 
signal via DBus. Bluetooth, however, never sent this signal, so when 
connman restarted I had two bluetooth technology entries in my UI. I 
traced it down to the fact that the rfkill_list in technology.c is 
static and never releases the technology by calling put_technology when 
cleaning up. So, this patch removes all rfkills in the list on cleanup 
so that all of the technologies are removed.

___
connman mailing list
connman@connman.net
https://lists.connman.net/mailman/listinfo/connman