0bddf4b5dbbb1eb3cc0c3280bb99b08e05632ba8
[kernel/swap-modules.git] / uihv / uihv_debugfs.c
1 #include <linux/fs.h>
2 #include <linux/slab.h>
3 #include <linux/debugfs.h>
4 #include <linux/module.h>
5 #include <asm/uaccess.h>
6 #include <master/swap_debugfs.h>
7 #include "uihv.h"
8 #include "uihv_module.h"
9
10 static const char UIHV_FOLDER[] = "uihv";
11 static const char UIHV_PATH[] = "path";
12 static const char UIHV_APP_INFO[] = "app_info";
13
14 static struct dentry *uihv_root;
15
16
17
18 /* ===========================================================================
19  * =                           UI VIEWER PATH                                =
20  * ===========================================================================
21  */
22
23
24 static ssize_t uihv_path_write(struct file *file, const char __user *buf,
25                                size_t len, loff_t *ppos)
26 {
27         ssize_t ret;
28         char *path;
29
30         path = kmalloc(len, GFP_KERNEL);
31         if (path == NULL) {
32                 ret = -ENOMEM;
33                 goto uihv_path_write_out;
34         }
35
36         if (copy_from_user(path, buf, len)) {
37                 ret = -EINVAL;
38                 goto uihv_path_write_out;
39         }
40
41         path[len - 1] = '\0';
42
43         if (uihv_set_handler(path) != 0) {
44                 printk(UIHV_PREFIX "Cannot set ui viewer path %s\n", path);
45                 ret = -EINVAL;
46                 goto uihv_path_write_out;
47         }
48
49         ret = len;
50
51         printk(UIHV_PREFIX "Set ui viewer path %s\n", path);
52
53 uihv_path_write_out:
54         kfree(path);
55
56         return ret;
57 }
58
59 static const struct file_operations uihv_path_file_ops = {
60         .owner = THIS_MODULE,
61         .write = uihv_path_write,
62 };
63
64
65 /*
66  * format:
67  *      main:app_path
68  *
69  * sample:
70  *      0x00000d60:/bin/app_sample
71  */
72 static int uihv_add_app_info(const char *buf, size_t len)
73 {
74         int n, ret;
75         char *app_path;
76         unsigned long main_addr;
77         const char fmt[] = "%%lx:/%%%ds";
78         char fmt_buf[64];
79
80         n = snprintf(fmt_buf, sizeof(fmt_buf), fmt, PATH_MAX - 2);
81         if (n <= 0)
82                 return -EINVAL;
83
84         app_path = kmalloc(PATH_MAX, GFP_KERNEL);
85         if (app_path == NULL)
86                 return -ENOMEM;
87
88         n = sscanf(buf, fmt_buf, &main_addr, app_path + 1);
89         if (n != 2) {
90                 ret = -EINVAL;
91                 goto free_app_path;
92         }
93         app_path[0] = '/';
94
95         printk(UIHV_PREFIX "Set ui viewer app path %s, main offset 0x%lx\n", app_path, main_addr);
96
97         ret = uihv_data_set(app_path, main_addr);
98
99 free_app_path:
100         kfree(app_path);
101         return ret;
102 }
103
104 static ssize_t write_uihv_app_info(struct file *file,
105                                         const char __user *user_buf,
106                                         size_t len, loff_t *ppos)
107 {
108         ssize_t ret = len;
109         char *buf;
110
111         buf = kmalloc(len, GFP_KERNEL);
112         if (buf == NULL) {
113                 ret = -ENOMEM;
114                 goto free_buf;
115         }
116
117         if (copy_from_user(buf, user_buf, len)) {
118                 ret = -EINVAL;
119                 goto free_buf;
120         }
121
122         buf[len - 1] = '\0';
123
124         if (uihv_add_app_info(buf, len))
125                 ret = -EINVAL;
126
127 free_buf:
128         kfree(buf);
129
130         return ret;
131 }
132
133 static const struct file_operations uihv_app_info_file_ops = {
134         .owner = THIS_MODULE,
135         .write =        write_uihv_app_info,
136 };
137
138
139 int uihv_dfs_init(void)
140 {
141         struct dentry *swap_dentry, *root, *path, *app_info;
142         int ret;
143
144         ret = -ENODEV;
145         if (!debugfs_initialized())
146                 goto fail;
147
148         ret = -ENOENT;
149         swap_dentry = swap_debugfs_getdir();
150         if (!swap_dentry)
151                 goto fail;
152
153         ret = -ENOMEM;
154         root = debugfs_create_dir(UIHV_FOLDER, swap_dentry);
155         if (IS_ERR_OR_NULL(root))
156                 goto fail;
157
158         uihv_root = root;
159
160         path = debugfs_create_file(UIHV_PATH, UIHV_DEFAULT_PERMS, root,
161                             NULL, &uihv_path_file_ops);
162         if (IS_ERR_OR_NULL(path)) {
163                 ret = -ENOMEM;
164                 goto remove;
165         }
166
167         app_info = debugfs_create_file(UIHV_APP_INFO, UIHV_DEFAULT_PERMS,
168                                 root, NULL, &uihv_app_info_file_ops);
169         if (IS_ERR_OR_NULL(app_info)) {
170                 ret = -ENOMEM;
171                 goto remove;
172         }
173
174         return 0;
175
176 remove:
177         debugfs_remove_recursive(root);
178
179 fail:
180         printk(UIHV_PREFIX "Debugfs initialization failure: %d\n", ret);
181
182         return ret;
183 }
184
185 void uihv_dfs_exit(void)
186 {
187         if (uihv_root)
188                 debugfs_remove_recursive(uihv_root);
189
190         uihv_root = NULL;
191 }