aboutsummaryrefslogtreecommitdiffstats
path: root/mm
diff options
context:
space:
mode:
authorVladimir Davydov <vdavydov@parallels.com>2014-10-09 18:28:43 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2014-10-09 22:25:59 -0400
commit33a690c45b202e4c6483bfd1d93ad8d0f51df2ca (patch)
tree7dd3e77ff0007b5c03dd9622f5d0b5e63bc357be /mm
parent7a82ca0d6437261d0727ce472ae4f3a05a9ce5f7 (diff)
memcg: move memcg_{alloc,free}_cache_params to slab_common.c
The only reason why they live in memcontrol.c is that we get/put css reference to the owner memory cgroup in them. However, we can do that in memcg_{un,}register_cache. OTOH, there are several reasons to move them to slab_common.c. First, I think that the less public interface functions we have in memcontrol.h the better. Since the functions I move don't depend on memcontrol, I think it's worth making them private to slab, especially taking into account that the arrays are defined on the slab's side too. Second, the way how per-memcg arrays are updated looks rather awkward: it proceeds from memcontrol.c (__memcg_activate_kmem) to slab_common.c (memcg_update_all_caches) and back to memcontrol.c again (memcg_update_array_size). In the following patches I move the function relocating the arrays (memcg_update_array_size) to slab_common.c and therefore get rid this circular call path. I think we should have the cache allocation stuff in the same place where we have relocation, because it's easier to follow the code then. So I move arrays alloc/free functions to slab_common.c too. The third point isn't obvious. I'm going to make the list_lru structure per-memcg to allow targeted kmem reclaim. That means we will have per-memcg arrays in list_lrus too. It turns out that it's much easier to update these arrays in list_lru.c rather than in memcontrol.c, because all the stuff we need is defined there. This patch makes memcg caches arrays allocation path conform that of the upcoming list_lru. So let's move these functions to slab_common.c and make them static. Signed-off-by: Vladimir Davydov <vdavydov@parallels.com> Acked-by: Johannes Weiner <hannes@cmpxchg.org> Acked-by: Michal Hocko <mhocko@suse.cz> Cc: Christoph Lameter <cl@linux.com> Cc: Glauber Costa <glommer@gmail.com> Cc: Joonsoo Kim <iamjoonsoo.kim@lge.com> Cc: David Rientjes <rientjes@google.com> Cc: Pekka Enberg <penberg@kernel.org> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'mm')
-rw-r--r--mm/memcontrol.c41
-rw-r--r--mm/slab_common.c44
2 files changed, 47 insertions, 38 deletions
diff --git a/mm/memcontrol.c b/mm/memcontrol.c
index 28928ce9b07f..865e87c014d6 100644
--- a/mm/memcontrol.c
+++ b/mm/memcontrol.c
@@ -2984,43 +2984,6 @@ int memcg_update_cache_size(struct kmem_cache *s, int num_groups)
2984 return 0; 2984 return 0;
2985} 2985}
2986 2986
2987int memcg_alloc_cache_params(struct mem_cgroup *memcg, struct kmem_cache *s,
2988 struct kmem_cache *root_cache)
2989{
2990 size_t size;
2991
2992 if (!memcg_kmem_enabled())
2993 return 0;
2994
2995 if (!memcg) {
2996 size = offsetof(struct memcg_cache_params, memcg_caches);
2997 size += memcg_limited_groups_array_size * sizeof(void *);
2998 } else
2999 size = sizeof(struct memcg_cache_params);
3000
3001 s->memcg_params = kzalloc(size, GFP_KERNEL);
3002 if (!s->memcg_params)
3003 return -ENOMEM;
3004
3005 if (memcg) {
3006 s->memcg_params->memcg = memcg;
3007 s->memcg_params->root_cache = root_cache;
3008 css_get(&memcg->css);
3009 } else
3010 s->memcg_params->is_root_cache = true;
3011
3012 return 0;
3013}
3014
3015void memcg_free_cache_params(struct kmem_cache *s)
3016{
3017 if (!s->memcg_params)
3018 return;
3019 if (!s->memcg_params->is_root_cache)
3020 css_put(&s->memcg_params->memcg->css);
3021 kfree(s->memcg_params);
3022}
3023
3024static void memcg_register_cache(struct mem_cgroup *memcg, 2987static void memcg_register_cache(struct mem_cgroup *memcg,
3025 struct kmem_cache *root_cache) 2988 struct kmem_cache *root_cache)
3026{ 2989{
@@ -3051,6 +3014,7 @@ static void memcg_register_cache(struct mem_cgroup *memcg,
3051 if (!cachep) 3014 if (!cachep)
3052 return; 3015 return;
3053 3016
3017 css_get(&memcg->css);
3054 list_add(&cachep->memcg_params->list, &memcg->memcg_slab_caches); 3018 list_add(&cachep->memcg_params->list, &memcg->memcg_slab_caches);
3055 3019
3056 /* 3020 /*
@@ -3084,6 +3048,9 @@ static void memcg_unregister_cache(struct kmem_cache *cachep)
3084 list_del(&cachep->memcg_params->list); 3048 list_del(&cachep->memcg_params->list);
3085 3049
3086 kmem_cache_destroy(cachep); 3050 kmem_cache_destroy(cachep);
3051
3052 /* drop the reference taken in memcg_register_cache */
3053 css_put(&memcg->css);
3087} 3054}
3088 3055
3089/* 3056/*
diff --git a/mm/slab_common.c b/mm/slab_common.c
index f206cb10a544..c2a8661f8b81 100644
--- a/mm/slab_common.c
+++ b/mm/slab_common.c
@@ -116,6 +116,38 @@ static inline int kmem_cache_sanity_check(const char *name, size_t size)
116#endif 116#endif
117 117
118#ifdef CONFIG_MEMCG_KMEM 118#ifdef CONFIG_MEMCG_KMEM
119static int memcg_alloc_cache_params(struct mem_cgroup *memcg,
120 struct kmem_cache *s, struct kmem_cache *root_cache)
121{
122 size_t size;
123
124 if (!memcg_kmem_enabled())
125 return 0;
126
127 if (!memcg) {
128 size = offsetof(struct memcg_cache_params, memcg_caches);
129 size += memcg_limited_groups_array_size * sizeof(void *);
130 } else
131 size = sizeof(struct memcg_cache_params);
132
133 s->memcg_params = kzalloc(size, GFP_KERNEL);
134 if (!s->memcg_params)
135 return -ENOMEM;
136
137 if (memcg) {
138 s->memcg_params->memcg = memcg;
139 s->memcg_params->root_cache = root_cache;
140 } else
141 s->memcg_params->is_root_cache = true;
142
143 return 0;
144}
145
146static void memcg_free_cache_params(struct kmem_cache *s)
147{
148 kfree(s->memcg_params);
149}
150
119int memcg_update_all_caches(int num_memcgs) 151int memcg_update_all_caches(int num_memcgs)
120{ 152{
121 struct kmem_cache *s; 153 struct kmem_cache *s;
@@ -141,7 +173,17 @@ out:
141 mutex_unlock(&slab_mutex); 173 mutex_unlock(&slab_mutex);
142 return ret; 174 return ret;
143} 175}
144#endif 176#else
177static inline int memcg_alloc_cache_params(struct mem_cgroup *memcg,
178 struct kmem_cache *s, struct kmem_cache *root_cache)
179{
180 return 0;
181}
182
183static inline void memcg_free_cache_params(struct kmem_cache *s)
184{
185}
186#endif /* CONFIG_MEMCG_KMEM */
145 187
146/* 188/*
147 * Find a mergeable slab cache 189 * Find a mergeable slab cache