mm/vmalloc: query dynamic DEBUG_PAGEALLOC setting
[cascardo/linux.git] / mm / memcontrol.c
index 42882c1..4b7dda7 100644 (file)
@@ -2325,9 +2325,6 @@ int __memcg_kmem_charge_memcg(struct page *page, gfp_t gfp, int order,
        struct page_counter *counter;
        int ret;
 
-       if (!memcg_kmem_online(memcg))
-               return 0;
-
        ret = try_charge(memcg, gfp, nr_pages);
        if (ret)
                return ret;
@@ -2346,10 +2343,11 @@ int __memcg_kmem_charge_memcg(struct page *page, gfp_t gfp, int order,
 int __memcg_kmem_charge(struct page *page, gfp_t gfp, int order)
 {
        struct mem_cgroup *memcg;
-       int ret;
+       int ret = 0;
 
        memcg = get_mem_cgroup_from_mm(current->mm);
-       ret = __memcg_kmem_charge_memcg(page, gfp, order, memcg);
+       if (memcg_kmem_online(memcg))
+               ret = __memcg_kmem_charge_memcg(page, gfp, order, memcg);
        css_put(&memcg->css);
        return ret;
 }
@@ -2719,39 +2717,48 @@ static int mem_cgroup_hierarchy_write(struct cgroup_subsys_state *css,
        return retval;
 }
 
-static unsigned long tree_stat(struct mem_cgroup *memcg,
-                              enum mem_cgroup_stat_index idx)
+static void tree_stat(struct mem_cgroup *memcg, unsigned long *stat)
 {
        struct mem_cgroup *iter;
-       unsigned long val = 0;
+       int i;
 
-       for_each_mem_cgroup_tree(iter, memcg)
-               val += mem_cgroup_read_stat(iter, idx);
+       memset(stat, 0, sizeof(*stat) * MEMCG_NR_STAT);
 
-       return val;
+       for_each_mem_cgroup_tree(iter, memcg) {
+               for (i = 0; i < MEMCG_NR_STAT; i++)
+                       stat[i] += mem_cgroup_read_stat(iter, i);
+       }
 }
 
-static unsigned long tree_events(struct mem_cgroup *memcg,
-                                enum mem_cgroup_events_index idx)
+static void tree_events(struct mem_cgroup *memcg, unsigned long *events)
 {
        struct mem_cgroup *iter;
-       unsigned long val = 0;
+       int i;
 
-       for_each_mem_cgroup_tree(iter, memcg)
-               val += mem_cgroup_read_events(iter, idx);
+       memset(events, 0, sizeof(*events) * MEMCG_NR_EVENTS);
 
-       return val;
+       for_each_mem_cgroup_tree(iter, memcg) {
+               for (i = 0; i < MEMCG_NR_EVENTS; i++)
+                       events[i] += mem_cgroup_read_events(iter, i);
+       }
 }
 
 static unsigned long mem_cgroup_usage(struct mem_cgroup *memcg, bool swap)
 {
-       unsigned long val;
+       unsigned long val = 0;
 
        if (mem_cgroup_is_root(memcg)) {
-               val = tree_stat(memcg, MEM_CGROUP_STAT_CACHE);
-               val += tree_stat(memcg, MEM_CGROUP_STAT_RSS);
-               if (swap)
-                       val += tree_stat(memcg, MEM_CGROUP_STAT_SWAP);
+               struct mem_cgroup *iter;
+
+               for_each_mem_cgroup_tree(iter, memcg) {
+                       val += mem_cgroup_read_stat(iter,
+                                       MEM_CGROUP_STAT_CACHE);
+                       val += mem_cgroup_read_stat(iter,
+                                       MEM_CGROUP_STAT_RSS);
+                       if (swap)
+                               val += mem_cgroup_read_stat(iter,
+                                               MEM_CGROUP_STAT_SWAP);
+               }
        } else {
                if (!swap)
                        val = page_counter_read(&memcg->memory);
@@ -5077,6 +5084,8 @@ static int memory_events_show(struct seq_file *m, void *v)
 static int memory_stat_show(struct seq_file *m, void *v)
 {
        struct mem_cgroup *memcg = mem_cgroup_from_css(seq_css(m));
+       unsigned long stat[MEMCG_NR_STAT];
+       unsigned long events[MEMCG_NR_EVENTS];
        int i;
 
        /*
@@ -5090,22 +5099,27 @@ static int memory_stat_show(struct seq_file *m, void *v)
         * Current memory state:
         */
 
+       tree_stat(memcg, stat);
+       tree_events(memcg, events);
+
        seq_printf(m, "anon %llu\n",
-                  (u64)tree_stat(memcg, MEM_CGROUP_STAT_RSS) * PAGE_SIZE);
+                  (u64)stat[MEM_CGROUP_STAT_RSS] * PAGE_SIZE);
        seq_printf(m, "file %llu\n",
-                  (u64)tree_stat(memcg, MEM_CGROUP_STAT_CACHE) * PAGE_SIZE);
+                  (u64)stat[MEM_CGROUP_STAT_CACHE] * PAGE_SIZE);
+       seq_printf(m, "kernel_stack %llu\n",
+                  (u64)stat[MEMCG_KERNEL_STACK] * PAGE_SIZE);
+       seq_printf(m, "slab %llu\n",
+                  (u64)(stat[MEMCG_SLAB_RECLAIMABLE] +
+                        stat[MEMCG_SLAB_UNRECLAIMABLE]) * PAGE_SIZE);
        seq_printf(m, "sock %llu\n",
-                  (u64)tree_stat(memcg, MEMCG_SOCK) * PAGE_SIZE);
+                  (u64)stat[MEMCG_SOCK] * PAGE_SIZE);
 
        seq_printf(m, "file_mapped %llu\n",
-                  (u64)tree_stat(memcg, MEM_CGROUP_STAT_FILE_MAPPED) *
-                  PAGE_SIZE);
+                  (u64)stat[MEM_CGROUP_STAT_FILE_MAPPED] * PAGE_SIZE);
        seq_printf(m, "file_dirty %llu\n",
-                  (u64)tree_stat(memcg, MEM_CGROUP_STAT_DIRTY) *
-                  PAGE_SIZE);
+                  (u64)stat[MEM_CGROUP_STAT_DIRTY] * PAGE_SIZE);
        seq_printf(m, "file_writeback %llu\n",
-                  (u64)tree_stat(memcg, MEM_CGROUP_STAT_WRITEBACK) *
-                  PAGE_SIZE);
+                  (u64)stat[MEM_CGROUP_STAT_WRITEBACK] * PAGE_SIZE);
 
        for (i = 0; i < NR_LRU_LISTS; i++) {
                struct mem_cgroup *mi;
@@ -5117,12 +5131,17 @@ static int memory_stat_show(struct seq_file *m, void *v)
                           mem_cgroup_lru_names[i], (u64)val * PAGE_SIZE);
        }
 
+       seq_printf(m, "slab_reclaimable %llu\n",
+                  (u64)stat[MEMCG_SLAB_RECLAIMABLE] * PAGE_SIZE);
+       seq_printf(m, "slab_unreclaimable %llu\n",
+                  (u64)stat[MEMCG_SLAB_UNRECLAIMABLE] * PAGE_SIZE);
+
        /* Accumulated memory events */
 
        seq_printf(m, "pgfault %lu\n",
-                  tree_events(memcg, MEM_CGROUP_EVENTS_PGFAULT));
+                  events[MEM_CGROUP_EVENTS_PGFAULT]);
        seq_printf(m, "pgmajfault %lu\n",
-                  tree_events(memcg, MEM_CGROUP_EVENTS_PGMAJFAULT));
+                  events[MEM_CGROUP_EVENTS_PGMAJFAULT]);
 
        return 0;
 }