This is a special case that happens if we for example stop
ConnMan while there is a pending DNS resolver going on.
Fixing this minor memory leak helps to catch the more
serious leaks in ConnMan.

Reported by Jaakko Hannikainen.
---
 vpn/vpn-provider.c | 18 ++++++++++++++++++
 1 file changed, 18 insertions(+)

diff --git a/vpn/vpn-provider.c b/vpn/vpn-provider.c
index 16c0c2b..b0aadcd 100644
--- a/vpn/vpn-provider.c
+++ b/vpn/vpn-provider.c
@@ -549,6 +549,12 @@ static void resolv_result(GResolvResultStatus status,
                provider->host_ip = g_strdupv(results);
 
        vpn_provider_unref(provider);
+
+       /* Remove the resolver here so that it will not be left
+        * hanging around and cause double free in unregister_provider()
+        */
+       g_resolv_unref(provider->resolv);
+       provider->resolv = NULL;
 }
 
 static void provider_resolv_host_addr(struct vpn_provider *provider)
@@ -1605,6 +1611,18 @@ static void unregister_provider(gpointer data)
 
        connection_unregister(provider);
 
+       /* If the provider has any DNS resolver queries pending,
+        * they need to be cleared here because the unref will not
+        * be able to do that (because the provider_resolv_host_addr()
+        * has increased the ref count by 1). This is quite rare as
+        * normally the resolving either returns a value or has a
+        * timeout which clears the memory. Typically resolv_result() will
+        * unref the provider but in this case that call has not yet
+        * happened.
+        */
+       if (provider->resolv)
+               vpn_provider_unref(provider);
+
        vpn_provider_unref(provider);
 }
 
-- 
2.1.0

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

Reply via email to