summaryrefslogtreecommitdiff
path: root/vpn
diff options
context:
space:
mode:
authorJussi Laakkonen <jussi.laakkonen@jolla.com>2020-12-02 11:22:11 +0200
committerDaniel Wagner <wagi@monom.org>2020-12-04 13:53:49 +0100
commitb07112e0428a0272a3ca5951426721c74b293674 (patch)
treeb1347ba041c000f00dd36be1f8a08f92e6bae2ed /vpn
parent3c9577e3feb0eb034250e974989c7f04827d48aa (diff)
downloadconnman-b07112e0428a0272a3ca5951426721c74b293674.tar.gz
vpn-provider: Cancel agent requests when removing VPN
If a VPN has a pending request active in the agent and connman-vpnd is restarted or shutdown it will result in segmentation fault. This happens because plugins and tasks are cleaned up before vpn-provider and thus, the removal of agent driver is called after the plugins are gone and if there is a pending request from any unloaded VPN plugin it needs to be cancelled. Since the callback set in the agent request points to a function in the VPN plugin following happens: Thread 1 "connman-vpnd" received signal SIGSEGV, Segmentation fault. 0xf6716cbc in ?? () (gdb) bt \#0 0xf6716cbc in ?? () \#1 0x0002bafc in agent_finalize_pending (reply=reply@entry=0x0, agent=<optimized out>) at src/agent.c:121 \#2 0x0002bd80 in cancel_all_requests (agent=0x5285a0) at src/agent.c:483 \#3 agent_unref_debug (file=0x363d4 "src/agent.c", line=647, caller=<synthetic pointer>, agent=0x5285a0) at src/agent.c:568 \#4 agent_destroy (data=0x5285a0) at src/agent.c:647 \#5 0xf6f6e8d6 in g_hash_table_remove_all_nodes (hash_table=0x4c94e8, notify=<optimized out>, destruction=<optimized out>) at ghash.c:552 \#6 0xf6f6fe3c in g_hash_table_remove_all_nodes (destruction=0, notify=1, hash_table=0x4c94e8) at ghash.c:1444 \#7 g_hash_table_remove_all (hash_table=0x4c94e8) at ghash.c:1447 \#8 0x0002c442 in connman_agent_driver_unregister (driver=driver@entry=0x49784 <agent_driver>) at src/agent.c:629 \#9 0x00024442 in __vpn_provider_cleanup () at vpn/vpn-provider.c:3416 \#10 0x0001a086 in main (argc=1, argv=0xff8c1334) at vpn/main.c:283 Therefore, the requests must be canceled at plugin driver unregister as that gets eventually called by VPN plugin exit function via vpn_unregister().
Diffstat (limited to 'vpn')
-rw-r--r--vpn/vpn-provider.c6
1 files changed, 6 insertions, 0 deletions
diff --git a/vpn/vpn-provider.c b/vpn/vpn-provider.c
index 5d0fb2ce..be25e394 100644
--- a/vpn/vpn-provider.c
+++ b/vpn/vpn-provider.c
@@ -2984,6 +2984,12 @@ void vpn_provider_driver_unregister(struct vpn_provider_driver *driver)
if (provider && provider->driver &&
g_strcmp0(provider->driver->name,
driver->name) == 0) {
+ /*
+ * Cancel VPN agent request to avoid segfault at
+ * shutdown as the callback, if set can point to a
+ * function in the plugin that is to be removed.
+ */
+ connman_agent_cancel(provider);
provider->driver = NULL;
}
}