[Devel] [PATCH rh7] cgroup: fix css_tryget() to not succeed on offlined css.

Andrey Ryabinin aryabinin at virtuozzo.com
Wed Jul 18 19:29:16 MSK 2018


We made the backport of the upstream commit d3daf28da16a ("cgroup: use percpu
refcnt for cgroup_subsys_states") which contains the following hunk:

@@ -123,11 +117,9 @@ static inline bool css_tryget(struct cgroup_subsys_state *css)
 {
        if (css->flags & CSS_ROOT)
                return true;
-       return __css_tryget(css);
+       return percpu_ref_tryget(&css->refcnt);

RedHat backpoted:
       2070d50e1cbe ("percpu-refcount: rename percpu_ref_tryget() to percpu_ref_tryget_live()")
       4fb6e25049cb ("percpu-refcount: implement percpu_ref_tryget()")

The first patch simply renames existed percpu_ref_tryget() to percpu_ref_tryget_live().
Upstream version obviously changes percpu_ref_tryget() in css_tryget()
to percpu_ref_tryget_live(). Redhat's version doesn't do that, because
css_tryget() doesn't use percpu counter in Redhat's kernel source.

The second patch adds new function percpu_ref_tryget() which our
css_tryget() wrongly uses. This may lead to successful css_tryget()
on offlined css, which shouldn't happen. And that may lead to all sorts
of issues like use-after-frees, crashes, etc...

Use percpu_ref_tryget_live() in css_tryget() to fix this.

https://jira.sw.ru/browse/PSBM-75892
Signed-off-by: Andrey Ryabinin <aryabinin at virtuozzo.com>
---
 include/linux/cgroup.h | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/include/linux/cgroup.h b/include/linux/cgroup.h
index e18fcd930eb1..9f43eb357c6a 100644
--- a/include/linux/cgroup.h
+++ b/include/linux/cgroup.h
@@ -167,7 +167,7 @@ static inline bool css_tryget(struct cgroup_subsys_state *css)
 {
 	if (css->flags & CSS_ROOT)
 		return true;
-	return percpu_ref_tryget(&css->refcnt);
+	return percpu_ref_tryget_live(&css->refcnt);
 }
 
 /*
-- 
2.16.4



More information about the Devel mailing list