[PATCH 2/2] agent: clear pending_id on request timeout
Inti Manuel Yabar-Pagaza <[email protected]>
| Newsgroups | dev.linux.lists.iwd |
|---|---|
| Message-ID | <5033e58b9c9305efe61f91b1757a4337f0424c33.1786525748.git.intimyp@gmail.com> |
request_timeout() cancels the outstanding call but leaves
agent->pending_id set. agent_finalize_pending() pops the last request
and agent_send_next_request() returns early on the empty queue, so the
stale id survives with nothing queued.
When the agent later drops off the bus, agent_disconnect() tests that
id and calls agent_finalize_pending() again, which pops NULL off the
empty queue and dereferences it:
#0 agent_finalize_pending (agent=0x..., reply=0x0) at src/agent.c:187
#1 agent_disconnect (...) at src/agent.c:511
#2 _dbus_name_cache_notify (...) at ell/dbus-name-cache.c:188
#4 name_owner_changed_cb (...) at ell/dbus.c:861
agent_receive_reply() and agent_request_cancel() already clear
pending_id in this situation. Do the same on timeout, and guard
agent_finalize_pending() against an empty queue.
Fixes: d04ab5ad96b4 ("agent: call back even if agent disconnects")
---
src/agent.c | 3 +++
1 file changed, 3 insertions(+)
diff --git a/src/agent.c b/src/agent.c
index 0f718b87..5adee5dc 100644
--- a/src/agent.c
+++ b/src/agent.c
@@ -183,6 +183,8 @@ static void agent_finalize_pending(struct agent *agent,
}
pending = l_queue_pop_head(agent->requests);
+ if (!pending)
+ return;
switch (pending->type) {
case AGENT_REQUEST_TYPE_PASSPHRASE:
@@ -230,6 +232,7 @@ static void request_timeout(struct l_timeout *timeout, void *user_data)
struct agent *agent = user_data;
l_dbus_cancel(dbus_get_bus(), agent->pending_id);
+ agent->pending_id = 0;
send_cancel_request(agent, -ETIMEDOUT);
--
2.55.0