From 9748b42bda634fa4409912c057acda105aff3c22 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Niklas=20Hamb=C3=BCchen?= Date: Sat, 6 Oct 2018 04:30:28 +0200 Subject: [PATCH] Fix FORCED_SHUTDOWN_THRESHOLD leak mitigation being skipped. On quickly incoming notifications, the bubble IDs can skip the FORCED_SHUTDOWN_THRESHOLD value compared to with ==, which means that the branch that shuts down the process will never be taken. Details: First an explanation of the quitting logic: if (bubble_get_id (bubble) == FORCED_SHUTDOWN_THRESHOLD) g_timeout_add (defaults_get_on_screen_timeout (self->defaults), _arm_forced_quit, (gpointer) self); The "bubble IDs" count upwards from 1, one for each notification bubble shown. When the bubble ID reaches FORCED_SHUTDOWN_THRESHOLD = 500, then _arm_forced_quit() is called, which quits the process using gtk_main_quit() and thus terminates notify-osd, and it is restarted automatically (I think by DBUS) when the next notification comes in. But this is only the case if you wait between your `notify-send mytext` invocations until the current bubble has faded out and is no longer shown. If you call `notify-send mytext` while the previous notification is still being displayed then bubble ID is actually 0. (This is because the variable `bubble` is NULL in that case, and bubble_get_id(NULL) returns 0.) But the bubble ID generation counter is still incremented nevertheless. So if your generated bubble IDs are 1, 2, and then 0, the next bubble ID generated will be 4. You can generate this situation e.g. this way (note that the default notification timeout is 10 seconds, so I sleep 11 seconds): notify-send test && sleep 11 && notify-send test && notify-send test && sleep 11 && notify-send test So when you send notifications in quick succession, their bubble IDs are skipped. Now, if you send them in quick succession around the 500th notification, then the check if (bubble_get_id (bubble) == FORCED_SHUTDOWN_THRESHOLD) will never trigger (e.g. because the bubble IDs will be 499, 0, and 501). Then the forced shutdown will never happen, and notify-osd will leak memory forever instead of being restarted every 500th notification. The fix is to use if (bubble_get_id (bubble) >= FORCED_SHUTDOWN_THRESHOLD) instead. --- src/stack.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/stack.c b/src/stack.c index 7b10048..77f2589 100644 --- a/src/stack.c +++ b/src/stack.c @@ -817,7 +817,7 @@ stack_notify_handler (Stack* self, // to be displayed), in order to get the leaked memory freed again, any // new notifications, coming in after the shutdown, will instruct the // session to restart notify-osd - if (bubble_get_id (bubble) == FORCED_SHUTDOWN_THRESHOLD) + if (bubble_get_id (bubble) >= FORCED_SHUTDOWN_THRESHOLD) g_timeout_add (defaults_get_on_screen_timeout (self->defaults), _arm_forced_quit, (gpointer) self); -- 2.12.2