mm: cma: allocation trigger
[linux-2.6-block.git] / mm / cma_debug.c
CommitLineData
28b24c1f
SL
1/*
2 * CMA DebugFS Interface
3 *
4 * Copyright (c) 2015 Sasha Levin <sasha.levin@oracle.com>
5 */
6
7
8#include <linux/debugfs.h>
9#include <linux/cma.h>
26b02a1f
SL
10#include <linux/list.h>
11#include <linux/kernel.h>
12#include <linux/slab.h>
28b24c1f
SL
13
14#include "cma.h"
15
26b02a1f
SL
16struct cma_mem {
17 struct hlist_node node;
18 struct page *p;
19 unsigned long n;
20};
21
28b24c1f
SL
22static struct dentry *cma_debugfs_root;
23
24static int cma_debugfs_get(void *data, u64 *val)
25{
26 unsigned long *p = data;
27
28 *val = *p;
29
30 return 0;
31}
32
33DEFINE_SIMPLE_ATTRIBUTE(cma_debugfs_fops, cma_debugfs_get, NULL, "%llu\n");
34
26b02a1f
SL
35static void cma_add_to_cma_mem_list(struct cma *cma, struct cma_mem *mem)
36{
37 spin_lock(&cma->mem_head_lock);
38 hlist_add_head(&mem->node, &cma->mem_head);
39 spin_unlock(&cma->mem_head_lock);
40}
41
42static int cma_alloc_mem(struct cma *cma, int count)
43{
44 struct cma_mem *mem;
45 struct page *p;
46
47 mem = kzalloc(sizeof(*mem), GFP_KERNEL);
48 if (!mem)
49 return -ENOMEM;
50
51 p = cma_alloc(cma, count, CONFIG_CMA_ALIGNMENT);
52 if (!p) {
53 kfree(mem);
54 return -ENOMEM;
55 }
56
57 mem->p = p;
58 mem->n = count;
59
60 cma_add_to_cma_mem_list(cma, mem);
61
62 return 0;
63}
64
65static int cma_alloc_write(void *data, u64 val)
66{
67 int pages = val;
68 struct cma *cma = data;
69
70 return cma_alloc_mem(cma, pages);
71}
72
73DEFINE_SIMPLE_ATTRIBUTE(cma_alloc_fops, NULL, cma_alloc_write, "%llu\n");
74
28b24c1f
SL
75static void cma_debugfs_add_one(struct cma *cma, int idx)
76{
77 struct dentry *tmp;
78 char name[16];
79 int u32s;
80
81 sprintf(name, "cma-%d", idx);
82
83 tmp = debugfs_create_dir(name, cma_debugfs_root);
84
26b02a1f
SL
85 debugfs_create_file("alloc", S_IWUSR, cma_debugfs_root, cma,
86 &cma_alloc_fops);
87
28b24c1f
SL
88 debugfs_create_file("base_pfn", S_IRUGO, tmp,
89 &cma->base_pfn, &cma_debugfs_fops);
90 debugfs_create_file("count", S_IRUGO, tmp,
91 &cma->count, &cma_debugfs_fops);
92 debugfs_create_file("order_per_bit", S_IRUGO, tmp,
26b02a1f 93 &cma->order_per_bit, &cma_debugfs_fops);
28b24c1f
SL
94
95 u32s = DIV_ROUND_UP(cma_bitmap_maxno(cma), BITS_PER_BYTE * sizeof(u32));
96 debugfs_create_u32_array("bitmap", S_IRUGO, tmp, (u32*)cma->bitmap, u32s);
97}
98
99static int __init cma_debugfs_init(void)
100{
101 int i;
102
103 cma_debugfs_root = debugfs_create_dir("cma", NULL);
104 if (!cma_debugfs_root)
105 return -ENOMEM;
106
107 for (i = 0; i < cma_area_count; i++)
108 cma_debugfs_add_one(&cma_areas[i], i);
109
110 return 0;
111}
112late_initcall(cma_debugfs_init);