aboutsummaryrefslogtreecommitdiffstats
path: root/kernel
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2016-10-14 15:18:50 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2016-10-14 15:18:50 -0400
commitf34d3606f76a8121b9d4940d2dd436bebeb2f9d7 (patch)
tree61a9deb6a950568df274580fbbd44a7015af9f7c /kernel
parentb6daa51b9a6a02a644dcf6b880fd50c1f70ec07f (diff)
parentbbb427e342495df1cda10051d0566388697499c0 (diff)
Merge branch 'for-4.9' of git://git.kernel.org/pub/scm/linux/kernel/git/tj/cgroup
Pull cgroup updates from Tejun Heo: - tracepoints for basic cgroup management operations added - kernfs and cgroup path formatting functions updated to behave in the style of strlcpy() - non-critical bug fixes * 'for-4.9' of git://git.kernel.org/pub/scm/linux/kernel/git/tj/cgroup: blkcg: Unlock blkcg_pol_mutex only once when cpd == NULL cgroup: fix error handling regressions in proc_cgroup_show() and cgroup_release_agent() cpuset: fix error handling regression in proc_cpuset_show() cgroup: add tracepoints for basic operations cgroup: make cgroup_path() and friends behave in the style of strlcpy() kernfs: remove kernfs_path_len() kernfs: make kernfs_path*() behave in the style of strlcpy() kernfs: add dummy implementation of kernfs_path_from_node()
Diffstat (limited to 'kernel')
-rw-r--r--kernel/cgroup.c75
-rw-r--r--kernel/cpuset.c13
-rw-r--r--kernel/sched/debug.c3
3 files changed, 57 insertions, 34 deletions
diff --git a/kernel/cgroup.c b/kernel/cgroup.c
index 44066158f0d1..85bc9beb046d 100644
--- a/kernel/cgroup.c
+++ b/kernel/cgroup.c
@@ -64,6 +64,9 @@
64#include <linux/file.h> 64#include <linux/file.h>
65#include <net/sock.h> 65#include <net/sock.h>
66 66
67#define CREATE_TRACE_POINTS
68#include <trace/events/cgroup.h>
69
67/* 70/*
68 * pidlists linger the following amount before being destroyed. The goal 71 * pidlists linger the following amount before being destroyed. The goal
69 * is avoiding frequent destruction in the middle of consecutive read calls 72 * is avoiding frequent destruction in the middle of consecutive read calls
@@ -1176,6 +1179,8 @@ static void cgroup_destroy_root(struct cgroup_root *root)
1176 struct cgroup *cgrp = &root->cgrp; 1179 struct cgroup *cgrp = &root->cgrp;
1177 struct cgrp_cset_link *link, *tmp_link; 1180 struct cgrp_cset_link *link, *tmp_link;
1178 1181
1182 trace_cgroup_destroy_root(root);
1183
1179 cgroup_lock_and_drain_offline(&cgrp_dfl_root.cgrp); 1184 cgroup_lock_and_drain_offline(&cgrp_dfl_root.cgrp);
1180 1185
1181 BUG_ON(atomic_read(&root->nr_cgrps)); 1186 BUG_ON(atomic_read(&root->nr_cgrps));
@@ -1874,6 +1879,9 @@ static int cgroup_remount(struct kernfs_root *kf_root, int *flags, char *data)
1874 strcpy(root->release_agent_path, opts.release_agent); 1879 strcpy(root->release_agent_path, opts.release_agent);
1875 spin_unlock(&release_agent_path_lock); 1880 spin_unlock(&release_agent_path_lock);
1876 } 1881 }
1882
1883 trace_cgroup_remount(root);
1884
1877 out_unlock: 1885 out_unlock:
1878 kfree(opts.release_agent); 1886 kfree(opts.release_agent);
1879 kfree(opts.name); 1887 kfree(opts.name);
@@ -2031,6 +2039,8 @@ static int cgroup_setup_root(struct cgroup_root *root, u16 ss_mask)
2031 if (ret) 2039 if (ret)
2032 goto destroy_root; 2040 goto destroy_root;
2033 2041
2042 trace_cgroup_setup_root(root);
2043
2034 /* 2044 /*
2035 * There must be no failure case after here, since rebinding takes 2045 * There must be no failure case after here, since rebinding takes
2036 * care of subsystems' refcounts, which are explicitly dropped in 2046 * care of subsystems' refcounts, which are explicitly dropped in
@@ -2315,22 +2325,18 @@ static struct file_system_type cgroup2_fs_type = {
2315 .fs_flags = FS_USERNS_MOUNT, 2325 .fs_flags = FS_USERNS_MOUNT,
2316}; 2326};
2317 2327
2318static char *cgroup_path_ns_locked(struct cgroup *cgrp, char *buf, size_t buflen, 2328static int cgroup_path_ns_locked(struct cgroup *cgrp, char *buf, size_t buflen,
2319 struct cgroup_namespace *ns) 2329 struct cgroup_namespace *ns)
2320{ 2330{
2321 struct cgroup *root = cset_cgroup_from_root(ns->root_cset, cgrp->root); 2331 struct cgroup *root = cset_cgroup_from_root(ns->root_cset, cgrp->root);
2322 int ret;
2323 2332
2324 ret = kernfs_path_from_node(cgrp->kn, root->kn, buf, buflen); 2333 return kernfs_path_from_node(cgrp->kn, root->kn, buf, buflen);
2325 if (ret < 0 || ret >= buflen)
2326 return NULL;
2327 return buf;
2328} 2334}
2329 2335
2330char *cgroup_path_ns(struct cgroup *cgrp, char *buf, size_t buflen, 2336int cgroup_path_ns(struct cgroup *cgrp, char *buf, size_t buflen,
2331 struct cgroup_namespace *ns) 2337 struct cgroup_namespace *ns)
2332{ 2338{
2333 char *ret; 2339 int ret;
2334 2340
2335 mutex_lock(&cgroup_mutex); 2341 mutex_lock(&cgroup_mutex);
2336 spin_lock_irq(&css_set_lock); 2342 spin_lock_irq(&css_set_lock);
@@ -2357,12 +2363,12 @@ EXPORT_SYMBOL_GPL(cgroup_path_ns);
2357 * 2363 *
2358 * Return value is the same as kernfs_path(). 2364 * Return value is the same as kernfs_path().
2359 */ 2365 */
2360char *task_cgroup_path(struct task_struct *task, char *buf, size_t buflen) 2366int task_cgroup_path(struct task_struct *task, char *buf, size_t buflen)
2361{ 2367{
2362 struct cgroup_root *root; 2368 struct cgroup_root *root;
2363 struct cgroup *cgrp; 2369 struct cgroup *cgrp;
2364 int hierarchy_id = 1; 2370 int hierarchy_id = 1;
2365 char *path = NULL; 2371 int ret;
2366 2372
2367 mutex_lock(&cgroup_mutex); 2373 mutex_lock(&cgroup_mutex);
2368 spin_lock_irq(&css_set_lock); 2374 spin_lock_irq(&css_set_lock);
@@ -2371,16 +2377,15 @@ char *task_cgroup_path(struct task_struct *task, char *buf, size_t buflen)
2371 2377
2372 if (root) { 2378 if (root) {
2373 cgrp = task_cgroup_from_root(task, root); 2379 cgrp = task_cgroup_from_root(task, root);
2374 path = cgroup_path_ns_locked(cgrp, buf, buflen, &init_cgroup_ns); 2380 ret = cgroup_path_ns_locked(cgrp, buf, buflen, &init_cgroup_ns);
2375 } else { 2381 } else {
2376 /* if no hierarchy exists, everyone is in "/" */ 2382 /* if no hierarchy exists, everyone is in "/" */
2377 if (strlcpy(buf, "/", buflen) < buflen) 2383 ret = strlcpy(buf, "/", buflen);
2378 path = buf;
2379 } 2384 }
2380 2385
2381 spin_unlock_irq(&css_set_lock); 2386 spin_unlock_irq(&css_set_lock);
2382 mutex_unlock(&cgroup_mutex); 2387 mutex_unlock(&cgroup_mutex);
2383 return path; 2388 return ret;
2384} 2389}
2385EXPORT_SYMBOL_GPL(task_cgroup_path); 2390EXPORT_SYMBOL_GPL(task_cgroup_path);
2386 2391
@@ -2830,6 +2835,10 @@ static int cgroup_attach_task(struct cgroup *dst_cgrp,
2830 ret = cgroup_migrate(leader, threadgroup, dst_cgrp->root); 2835 ret = cgroup_migrate(leader, threadgroup, dst_cgrp->root);
2831 2836
2832 cgroup_migrate_finish(&preloaded_csets); 2837 cgroup_migrate_finish(&preloaded_csets);
2838
2839 if (!ret)
2840 trace_cgroup_attach_task(dst_cgrp, leader, threadgroup);
2841
2833 return ret; 2842 return ret;
2834} 2843}
2835 2844
@@ -3611,6 +3620,8 @@ static int cgroup_rename(struct kernfs_node *kn, struct kernfs_node *new_parent,
3611 mutex_lock(&cgroup_mutex); 3620 mutex_lock(&cgroup_mutex);
3612 3621
3613 ret = kernfs_rename(kn, new_parent, new_name_str); 3622 ret = kernfs_rename(kn, new_parent, new_name_str);
3623 if (!ret)
3624 trace_cgroup_rename(cgrp);
3614 3625
3615 mutex_unlock(&cgroup_mutex); 3626 mutex_unlock(&cgroup_mutex);
3616 3627
@@ -4381,6 +4392,8 @@ int cgroup_transfer_tasks(struct cgroup *to, struct cgroup *from)
4381 4392
4382 if (task) { 4393 if (task) {
4383 ret = cgroup_migrate(task, false, to->root); 4394 ret = cgroup_migrate(task, false, to->root);
4395 if (!ret)
4396 trace_cgroup_transfer_tasks(to, task, false);
4384 put_task_struct(task); 4397 put_task_struct(task);
4385 } 4398 }
4386 } while (task && !ret); 4399 } while (task && !ret);
@@ -5046,6 +5059,8 @@ static void css_release_work_fn(struct work_struct *work)
5046 ss->css_released(css); 5059 ss->css_released(css);
5047 } else { 5060 } else {
5048 /* cgroup release path */ 5061 /* cgroup release path */
5062 trace_cgroup_release(cgrp);
5063
5049 cgroup_idr_remove(&cgrp->root->cgroup_idr, cgrp->id); 5064 cgroup_idr_remove(&cgrp->root->cgroup_idr, cgrp->id);
5050 cgrp->id = -1; 5065 cgrp->id = -1;
5051 5066
@@ -5332,6 +5347,8 @@ static int cgroup_mkdir(struct kernfs_node *parent_kn, const char *name,
5332 if (ret) 5347 if (ret)
5333 goto out_destroy; 5348 goto out_destroy;
5334 5349
5350 trace_cgroup_mkdir(cgrp);
5351
5335 /* let's create and online css's */ 5352 /* let's create and online css's */
5336 kernfs_activate(kn); 5353 kernfs_activate(kn);
5337 5354
@@ -5507,6 +5524,9 @@ static int cgroup_rmdir(struct kernfs_node *kn)
5507 5524
5508 ret = cgroup_destroy_locked(cgrp); 5525 ret = cgroup_destroy_locked(cgrp);
5509 5526
5527 if (!ret)
5528 trace_cgroup_rmdir(cgrp);
5529
5510 cgroup_kn_unlock(kn); 5530 cgroup_kn_unlock(kn);
5511 return ret; 5531 return ret;
5512} 5532}
@@ -5743,7 +5763,7 @@ core_initcall(cgroup_wq_init);
5743int proc_cgroup_show(struct seq_file *m, struct pid_namespace *ns, 5763int proc_cgroup_show(struct seq_file *m, struct pid_namespace *ns,
5744 struct pid *pid, struct task_struct *tsk) 5764 struct pid *pid, struct task_struct *tsk)
5745{ 5765{
5746 char *buf, *path; 5766 char *buf;
5747 int retval; 5767 int retval;
5748 struct cgroup_root *root; 5768 struct cgroup_root *root;
5749 5769
@@ -5786,18 +5806,18 @@ int proc_cgroup_show(struct seq_file *m, struct pid_namespace *ns,
5786 * " (deleted)" is appended to the cgroup path. 5806 * " (deleted)" is appended to the cgroup path.
5787 */ 5807 */
5788 if (cgroup_on_dfl(cgrp) || !(tsk->flags & PF_EXITING)) { 5808 if (cgroup_on_dfl(cgrp) || !(tsk->flags & PF_EXITING)) {
5789 path = cgroup_path_ns_locked(cgrp, buf, PATH_MAX, 5809 retval = cgroup_path_ns_locked(cgrp, buf, PATH_MAX,
5790 current->nsproxy->cgroup_ns); 5810 current->nsproxy->cgroup_ns);
5791 if (!path) { 5811 if (retval >= PATH_MAX)
5792 retval = -ENAMETOOLONG; 5812 retval = -ENAMETOOLONG;
5813 if (retval < 0)
5793 goto out_unlock; 5814 goto out_unlock;
5794 } 5815
5816 seq_puts(m, buf);
5795 } else { 5817 } else {
5796 path = "/"; 5818 seq_puts(m, "/");
5797 } 5819 }
5798 5820
5799 seq_puts(m, path);
5800
5801 if (cgroup_on_dfl(cgrp) && cgroup_is_dead(cgrp)) 5821 if (cgroup_on_dfl(cgrp) && cgroup_is_dead(cgrp))
5802 seq_puts(m, " (deleted)\n"); 5822 seq_puts(m, " (deleted)\n");
5803 else 5823 else
@@ -6062,8 +6082,9 @@ static void cgroup_release_agent(struct work_struct *work)
6062{ 6082{
6063 struct cgroup *cgrp = 6083 struct cgroup *cgrp =
6064 container_of(work, struct cgroup, release_agent_work); 6084 container_of(work, struct cgroup, release_agent_work);
6065 char *pathbuf = NULL, *agentbuf = NULL, *path; 6085 char *pathbuf = NULL, *agentbuf = NULL;
6066 char *argv[3], *envp[3]; 6086 char *argv[3], *envp[3];
6087 int ret;
6067 6088
6068 mutex_lock(&cgroup_mutex); 6089 mutex_lock(&cgroup_mutex);
6069 6090
@@ -6073,13 +6094,13 @@ static void cgroup_release_agent(struct work_struct *work)
6073 goto out; 6094 goto out;
6074 6095
6075 spin_lock_irq(&css_set_lock); 6096 spin_lock_irq(&css_set_lock);
6076 path = cgroup_path_ns_locked(cgrp, pathbuf, PATH_MAX, &init_cgroup_ns); 6097 ret = cgroup_path_ns_locked(cgrp, pathbuf, PATH_MAX, &init_cgroup_ns);
6077 spin_unlock_irq(&css_set_lock); 6098 spin_unlock_irq(&css_set_lock);
6078 if (!path) 6099 if (ret < 0 || ret >= PATH_MAX)
6079 goto out; 6100 goto out;
6080 6101
6081 argv[0] = agentbuf; 6102 argv[0] = agentbuf;
6082 argv[1] = path; 6103 argv[1] = pathbuf;
6083 argv[2] = NULL; 6104 argv[2] = NULL;
6084 6105
6085 /* minimal command environment */ 6106 /* minimal command environment */
diff --git a/kernel/cpuset.c b/kernel/cpuset.c
index 2b4c20ab5bbe..29f815d2ef7e 100644
--- a/kernel/cpuset.c
+++ b/kernel/cpuset.c
@@ -2715,7 +2715,7 @@ void __cpuset_memory_pressure_bump(void)
2715int proc_cpuset_show(struct seq_file *m, struct pid_namespace *ns, 2715int proc_cpuset_show(struct seq_file *m, struct pid_namespace *ns,
2716 struct pid *pid, struct task_struct *tsk) 2716 struct pid *pid, struct task_struct *tsk)
2717{ 2717{
2718 char *buf, *p; 2718 char *buf;
2719 struct cgroup_subsys_state *css; 2719 struct cgroup_subsys_state *css;
2720 int retval; 2720 int retval;
2721 2721
@@ -2724,14 +2724,15 @@ int proc_cpuset_show(struct seq_file *m, struct pid_namespace *ns,
2724 if (!buf) 2724 if (!buf)
2725 goto out; 2725 goto out;
2726 2726
2727 retval = -ENAMETOOLONG;
2728 css = task_get_css(tsk, cpuset_cgrp_id); 2727 css = task_get_css(tsk, cpuset_cgrp_id);
2729 p = cgroup_path_ns(css->cgroup, buf, PATH_MAX, 2728 retval = cgroup_path_ns(css->cgroup, buf, PATH_MAX,
2730 current->nsproxy->cgroup_ns); 2729 current->nsproxy->cgroup_ns);
2731 css_put(css); 2730 css_put(css);
2732 if (!p) 2731 if (retval >= PATH_MAX)
2732 retval = -ENAMETOOLONG;
2733 if (retval < 0)
2733 goto out_free; 2734 goto out_free;
2734 seq_puts(m, p); 2735 seq_puts(m, buf);
2735 seq_putc(m, '\n'); 2736 seq_putc(m, '\n');
2736 retval = 0; 2737 retval = 0;
2737out_free: 2738out_free:
diff --git a/kernel/sched/debug.c b/kernel/sched/debug.c
index 13935886a471..fa178b62ea79 100644
--- a/kernel/sched/debug.c
+++ b/kernel/sched/debug.c
@@ -415,7 +415,8 @@ static char *task_group_path(struct task_group *tg)
415 if (autogroup_path(tg, group_path, PATH_MAX)) 415 if (autogroup_path(tg, group_path, PATH_MAX))
416 return group_path; 416 return group_path;
417 417
418 return cgroup_path(tg->css.cgroup, group_path, PATH_MAX); 418 cgroup_path(tg->css.cgroup, group_path, PATH_MAX);
419 return group_path;
419} 420}
420#endif 421#endif
421 422