Skip to content

Commit

Permalink
cgroup: add cgroup_v1v2_get_from_[fd/file]()
Browse files Browse the repository at this point in the history
Add cgroup_v1v2_get_from_fd() and cgroup_v1v2_get_from_file() that
support both cgroup1 and cgroup2.

Signed-off-by: Yosry Ahmed <[email protected]>
Signed-off-by: Tejun Heo <[email protected]>
  • Loading branch information
yosrym93 authored and htejun committed Oct 11, 2022
1 parent 03db771 commit a6d1ce5
Show file tree
Hide file tree
Showing 2 changed files with 45 additions and 6 deletions.
1 change: 1 addition & 0 deletions include/linux/cgroup.h
Original file line number Diff line number Diff line change
Expand Up @@ -106,6 +106,7 @@ struct cgroup_subsys_state *css_tryget_online_from_dir(struct dentry *dentry,

struct cgroup *cgroup_get_from_path(const char *path);
struct cgroup *cgroup_get_from_fd(int fd);
struct cgroup *cgroup_v1v2_get_from_fd(int fd);

int cgroup_attach_task_all(struct task_struct *from, struct task_struct *);
int cgroup_transfer_tasks(struct cgroup *to, struct cgroup *from);
Expand Down
50 changes: 44 additions & 6 deletions kernel/cgroup/cgroup.c
Original file line number Diff line number Diff line change
Expand Up @@ -6224,16 +6224,36 @@ void cgroup_fork(struct task_struct *child)
INIT_LIST_HEAD(&child->cg_list);
}

static struct cgroup *cgroup_get_from_file(struct file *f)
/**
* cgroup_v1v2_get_from_file - get a cgroup pointer from a file pointer
* @f: file corresponding to cgroup_dir
*
* Find the cgroup from a file pointer associated with a cgroup directory.
* Returns a pointer to the cgroup on success. ERR_PTR is returned if the
* cgroup cannot be found.
*/
static struct cgroup *cgroup_v1v2_get_from_file(struct file *f)
{
struct cgroup_subsys_state *css;
struct cgroup *cgrp;

css = css_tryget_online_from_dir(f->f_path.dentry, NULL);
if (IS_ERR(css))
return ERR_CAST(css);

cgrp = css->cgroup;
return css->cgroup;
}

/**
* cgroup_get_from_file - same as cgroup_v1v2_get_from_file, but only supports
* cgroup2.
*/
static struct cgroup *cgroup_get_from_file(struct file *f)
{
struct cgroup *cgrp = cgroup_v1v2_get_from_file(f);

if (IS_ERR(cgrp))
return ERR_CAST(cgrp);

if (!cgroup_on_dfl(cgrp)) {
cgroup_put(cgrp);
return ERR_PTR(-EBADF);
Expand Down Expand Up @@ -6734,14 +6754,14 @@ EXPORT_SYMBOL_GPL(cgroup_get_from_path);

/**
* cgroup_get_from_fd - get a cgroup pointer from a fd
* @fd: fd obtained by open(cgroup2_dir)
* @fd: fd obtained by open(cgroup_dir)
*
* Find the cgroup from a fd which should be obtained
* by opening a cgroup directory. Returns a pointer to the
* cgroup on success. ERR_PTR is returned if the cgroup
* cannot be found.
*/
struct cgroup *cgroup_get_from_fd(int fd)
struct cgroup *cgroup_v1v2_get_from_fd(int fd)
{
struct cgroup *cgrp;
struct file *f;
Expand All @@ -6750,10 +6770,28 @@ struct cgroup *cgroup_get_from_fd(int fd)
if (!f)
return ERR_PTR(-EBADF);

cgrp = cgroup_get_from_file(f);
cgrp = cgroup_v1v2_get_from_file(f);
fput(f);
return cgrp;
}

/**
* cgroup_get_from_fd - same as cgroup_v1v2_get_from_fd, but only supports
* cgroup2.
*/
struct cgroup *cgroup_get_from_fd(int fd)
{
struct cgroup *cgrp = cgroup_v1v2_get_from_fd(fd);

if (IS_ERR(cgrp))
return ERR_CAST(cgrp);

if (!cgroup_on_dfl(cgrp)) {
cgroup_put(cgrp);
return ERR_PTR(-EBADF);
}
return cgrp;
}
EXPORT_SYMBOL_GPL(cgroup_get_from_fd);

static u64 power_of_ten(int power)
Expand Down

0 comments on commit a6d1ce5

Please sign in to comment.