4 #include "kerncompat.h"
5 #include "radix-tree.h"
8 #include "print-tree.h"
12 static int setup_key(struct radix_tree_root *root, struct key *key, int exists)
21 ret = radix_tree_gang_lookup(root, (void **)res, num, 2);
26 } else if (ret != 0 && num == res[0]) {
28 if (ret > 1 && num == res[1]) {
37 static int ins_one(struct ctree_root *root, struct radix_tree_root *radix)
39 struct ctree_path path;
44 ret = setup_key(radix, &key, 0);
45 sprintf(buf, "str-%Lu\n", key.objectid);
46 ret = insert_item(root, &key, buf, strlen(buf));
49 radix_tree_preload(GFP_KERNEL);
50 ret = radix_tree_insert(radix, key.objectid,
51 (void *)key.objectid);
52 radix_tree_preload_end();
57 printf("failed to insert %Lu\n", key.objectid);
61 static int insert_dup(struct ctree_root *root, struct radix_tree_root *radix)
63 struct ctree_path path;
68 ret = setup_key(radix, &key, 1);
71 sprintf(buf, "str-%Lu\n", key.objectid);
72 ret = insert_item(root, &key, buf, strlen(buf));
74 printf("insert on %Lu gave us %d\n", key.objectid, ret);
80 static int del_one(struct ctree_root *root, struct radix_tree_root *radix)
82 struct ctree_path path;
87 ret = setup_key(radix, &key, 1);
90 ret = search_slot(root, &key, &path, -1);
93 ret = del_item(root, &path);
94 release_path(root, &path);
97 ptr = radix_tree_delete(radix, key.objectid);
102 printf("failed to delete %Lu\n", key.objectid);
106 static int lookup_item(struct ctree_root *root, struct radix_tree_root *radix)
108 struct ctree_path path;
112 ret = setup_key(radix, &key, 1);
115 ret = search_slot(root, &key, &path, 0);
116 release_path(root, &path);
121 printf("unable to find key %Lu\n", key.objectid);
125 static int lookup_enoent(struct ctree_root *root, struct radix_tree_root *radix)
127 struct ctree_path path;
131 ret = setup_key(radix, &key, 0);
134 ret = search_slot(root, &key, &path, 0);
135 release_path(root, &path);
140 printf("able to find key that should not exist %Lu\n", key.objectid);
144 int (*ops[])(struct ctree_root *root, struct radix_tree_root *radix) =
145 { ins_one, insert_dup, del_one, lookup_item, lookup_enoent };
147 static int fill_radix(struct ctree_root *root, struct radix_tree_root *radix)
149 struct ctree_path path;
157 key.objectid = (unsigned long)-1;
160 ret = search_slot(root, &key, &path, 0);
161 slot = path.slots[0];
164 release_path(root, &path);
169 for (i = slot; i >= 0; i--) {
170 found = path.nodes[0]->leaf.items[i].key.objectid;
171 radix_tree_preload(GFP_KERNEL);
172 ret = radix_tree_insert(radix, found, (void *)found);
175 "failed to insert %lu into radix\n",
180 radix_tree_preload_end();
182 release_path(root, &path);
183 key.objectid = found - 1;
184 if (key.objectid > found)
190 void sigstopper(int ignored)
193 fprintf(stderr, "caught exit signal, stopping\n");
196 int print_usage(void)
198 printf("usage: tester [-ih] [-c count] [-f count]\n");
199 printf("\t -c count -- iteration count after filling\n");
200 printf("\t -f count -- run this many random inserts before starting\n");
201 printf("\t -i -- only do initial fill\n");
202 printf("\t -h -- this help text\n");
205 int main(int ac, char **av)
207 RADIX_TREE(radix, GFP_KERNEL);
208 struct ctree_super_block super;
209 struct ctree_root *root;
214 int iterations = 20000;
215 int init_fill_count = 800000;
217 int initial_only = 0;
219 root = open_ctree("dbfile", &super);
220 fill_radix(root, &radix);
222 signal(SIGTERM, sigstopper);
223 signal(SIGINT, sigstopper);
225 for (i = 1 ; i < ac ; i++) {
226 if (strcmp(av[i], "-i") == 0) {
228 } else if (strcmp(av[i], "-c") == 0) {
229 iterations = atoi(av[i+1]);
231 } else if (strcmp(av[i], "-f") == 0) {
232 init_fill_count = atoi(av[i+1]);
238 for (i = 0; i < init_fill_count; i++) {
239 ret = ins_one(root, &radix);
241 printf("initial fill failed\n");
245 if (i % 10000 == 0) {
246 printf("initial fill %d level %d count %d\n", i,
247 node_level(root->node->node.header.flags),
248 root->node->node.header.nritems);
250 if (keep_running == 0) {
255 if (initial_only == 1) {
258 for (i = 0; i < iterations; i++) {
259 op = rand() % ARRAY_SIZE(ops);
260 count = rand() % 128;
265 if (i && i % 5000 == 0) {
266 printf("open & close, root level %d nritems %d\n",
267 node_level(root->node->node.header.flags),
268 root->node->node.header.nritems);
269 write_ctree_super(root, &super);
271 root = open_ctree("dbfile", &super);
274 ret = ops[op](root, &radix);
276 fprintf(stderr, "op %d failed %d:%d\n",
278 print_tree(root, root->node);
279 fprintf(stderr, "op %d failed %d:%d\n",
284 if (keep_running == 0) {
291 write_ctree_super(root, &super);