diff options
author | Jonny Lamb <jonny.lamb@collabora.co.uk> | 2011-04-05 16:57:11 +0100 |
---|---|---|
committer | Jonny Lamb <jonny.lamb@collabora.co.uk> | 2011-04-05 17:03:42 +0100 |
commit | 9d4802deb229e4a104c5dabea9fb1575c4cdd106 (patch) | |
tree | 71516014943a0054aee6e7f45142d98d6b46d75a | |
parent | 63b8269d73a285dd35873a843d52674869c6ddf3 (diff) |
meta-porter: don't start multiple timeouts for freeing the PorterData
1. open a connection to a contact
2. create a PorterData struct, the timeout starts
3. call hold, the timeout stops
4. remote contact closes connection, the porter disappears and the
timeout stops
5. call unhold, the refcount is now 0 so the timeout starts
6. a new connection appears for the contact so it's referenced by the
PorterData struct and a timeout is started
BINGO! THAT'S TWO TIMEOUTS STARTED!
7. the first timeout is called, the porter is closed and struct
freed
8. the second timeout is called, the struct is already freed so we
crash here
I think this is the right fix, because this means that if you hold()
the PorterData struct will stay around, but if you unhold() it will
disappear.
Signed-off-by: Jonny Lamb <jonny.lamb@collabora.co.uk>
-rw-r--r-- | wocky/wocky-meta-porter.c | 5 |
1 files changed, 5 insertions, 0 deletions
diff --git a/wocky/wocky-meta-porter.c b/wocky/wocky-meta-porter.c index edd1d95..5eff152 100644 --- a/wocky/wocky-meta-porter.c +++ b/wocky/wocky-meta-porter.c @@ -239,6 +239,11 @@ maybe_start_timeout (PorterData *data) { if (data->refcount == 0) { + /* if we've already got a timeout going let's cancel it and get + * a new one going instead of having two. */ + if (data->timeout_id > 0) + g_source_remove (data->timeout_id); + DEBUG ("Started porter timeout..."); data->timeout_id = g_timeout_add_seconds (5, porter_timeout_cb, data); } |