pass: resmon: Fix unneeded g_list_remove call when updating timer interval 93/224393/2
authorChanwoo Choi <cw00.choi@samsung.com>
Mon, 10 Feb 2020 07:31:44 +0000 (16:31 +0900)
committerChanwoo Choi <cw00.choi@samsung.com>
Mon, 10 Feb 2020 09:15:38 +0000 (18:15 +0900)
The commit 204e36c7c18a ("pass: resmon: Add new Resource Monitor (resmon)
module") added 'resmon_timer_add()' function which support two case as
following:
- case 1: Create timer with timer interval and add created timer to timer_list
- case 2: Update timer interval of already created timer in timer_list

In case 2, resmon_timer_add() had a bug about freeing resource because
don't need to remove a timer from 'resmon->timer_list' by using g_list_remove.

So that in order to fix this issue, do refactor the body of resmon_timer_add().

Change-Id: Iee76e42dd1eb92675e626d91e25f0672477fc3cc
Fixes: 204e36c7c18a ("pass: resmon: Add new Resource Monitor (resmon) module")
Signed-off-by: Chanwoo Choi <cw00.choi@samsung.com>
src/pass/pass-resmon.c

index 074eda8..b81a868 100644 (file)
@@ -161,39 +161,42 @@ static int resmon_timer_add(struct resmon *monitor, unsigned int interval)
        struct pass_resmon *resmon = monitor->resmon;
        int ret;
 
-       /* Add new timer-based resmon to timer_list if it's not created */
+       /* Add new timer-based resmon to timer_list */
        if (!resmon_is_created(resmon, RESMON_TIMER, monitor->src_type)) {
-               resmon->timer_list =
-                               g_list_append(resmon->timer_list,
-                                               (gpointer)monitor);
-               resmon->timer_state |= monitor->src_type;
+               monitor->timer_id = g_timeout_add((guint)interval,
+                                       (GSourceFunc)resmon_timer_func,
+                                       (gpointer)monitor);
+               if (!monitor->timer_id)
+                       return -EPERM;
+               monitor->timer_interval = interval;
 
                if (monitor->ops && monitor->ops->init) {
                        ret = monitor->ops->init(monitor);
-                       if (ret < 0)
+                       if (ret < 0) {
+                               g_source_remove(monitor->timer_id);
+                               monitor->timer_interval = 0;
                                return ret;
+                       }
                }
-       /*
-        * Remove the registered timer-based resmon in order to update interval
-        * of timer-based resmon if it's already created.
-        */
+
+               resmon->timer_list = g_list_append(resmon->timer_list,
+                                               (gpointer)monitor);
+               resmon->timer_state |= monitor->src_type;
+
+       /* Update timer interval of the registered timer-based resmon */
        } else {
                g_source_remove(monitor->timer_id);
-       }
+               monitor->timer_interval = 0;
 
-       /* Add timer-based resmon with new interval to update the interval */
-       monitor->timer_id = g_timeout_add((guint)interval,
-                               (GSourceFunc)resmon_timer_func,
-                               (gpointer)monitor);
-       if (!monitor->timer_id) {
-               resmon->timer_list = g_list_remove(resmon->timer_list,
-                                               (gpointer)monitor);
-               resmon->timer_state &= ~monitor->src_type;
-               return -EPERM;
+               /* Update timer interval of timer-based resmon */
+               monitor->timer_id = g_timeout_add((guint)interval,
+                                       (GSourceFunc)resmon_timer_func,
+                                       (gpointer)monitor);
+               if (!monitor->timer_id)
+                       return -EPERM;
+               monitor->timer_interval = interval;
        }
 
-       monitor->timer_interval = interval;
-
        return 0;
 }