@@ -28,6 +28,23 @@ extern bool frozen(struct task_struct *p);
extern bool freezing_slow_path(struct task_struct *p);
+extern enum freezing_reason freezing_reason_slow_path(struct task_struct *p);
+
+enum freezing_reason {
+ FREEZING_NONE = 0,
+ FREEZING_CGROUP = (1 << 0),
+ FREEZING_PM = (1 << 1),
+ FREEZING_PM_NOSIG = (1 << 2),
+};
+
+static inline enum freezing_reason freezing_reason(struct task_struct *p)
+{
+ if (static_branch_unlikely(&freezer_active))
+ return freezing_reason_slow_path(p);
+
+ return FREEZING_NONE;
+}
+
/*
* Check if there is a request to freeze a process
*/
@@ -26,6 +26,21 @@ bool pm_nosig_freezing;
/* protects freezing and frozen transitions */
static DEFINE_SPINLOCK(freezer_lock);
+enum freezing_reason freezing_reason_slow_path(struct task_struct *p)
+{
+ if (pm_nosig_freezing)
+ return FREEZING_PM_NOSIG;
+
+ if (cgroup_freezing(p))
+ return FREEZING_CGROUP;
+
+ if (pm_freezing && !(p->flags & PF_KTHREAD))
+ return FREEZING_PM;
+
+ return FREEZING_NONE;
+}
+EXPORT_SYMBOL(freezing_reason_slow_path);
+
/**
* freezing_slow_path - slow path for testing whether a task needs to be frozen
* @p: task to be tested
@@ -43,13 +58,7 @@ bool freezing_slow_path(struct task_struct *p)
if (test_tsk_thread_flag(p, TIF_MEMDIE))
return false;
- if (pm_nosig_freezing || cgroup_freezing(p))
- return true;
-
- if (pm_freezing && !(p->flags & PF_KTHREAD))
- return true;
-
- return false;
+ return (bool)freezing_reason_slow_path(p);
}
EXPORT_SYMBOL(freezing_slow_path);
There are few reasons why a task is freezing. It can be due to system suspend, it can be due to explicit user request, etc. For most cases, the actual reason is not important, but there are some that it is useful to distinguish between what actually caused the task to freeze. One example is when user requests freezing of tasks belonging to a certain cgroup. If for any reason, system goes suspend and resume when the cgroup is frozen, the already frozen tasks should not be thawed but remain frozen to ensure the suspend/resume cycle transparency. The system should not warn about skipping thawing of such processes as it is normal situation. The proposed function allows to obtain information about the freezing reason and let the calling code decide what to do accordingly. Signed-off-by: Michal Dubiel <md@chromium.org> --- include/linux/freezer.h | 17 +++++++++++++++ kernel/freezer.c | 23 ++++++++++++++------ 2 files changed, 33 insertions(+), 7 deletions(-)