Convert maps.c over to use list.h
[trinity.git] / maps.c
blobbbade0ff1ccc2ce1262f3214e8c3c7f7e7b08c4a
1 #include <errno.h>
2 #include <fcntl.h>
3 #include <malloc.h>
4 #include <stdio.h>
5 #include <stdlib.h>
6 #include <string.h>
7 #include <unistd.h>
8 #include <sys/mman.h>
9 #include <sys/types.h>
10 #include <sys/stat.h>
11 #include "trinity.h" // page_size
12 #include "arch.h"
13 #include "maps.h"
14 #include "list.h"
15 #include "log.h"
16 #include "shm.h"
17 #include "utils.h"
19 static unsigned int num_mappings = 0;
20 static struct map *maps = NULL;
22 char *page_zeros;
23 char *page_0xff;
24 char *page_rand;
25 char *page_allocs;
27 void * alloc_shared(unsigned int size)
29 void *ret;
31 ret = mmap(NULL, size, PROT_READ | PROT_WRITE, MAP_ANON | MAP_SHARED, -1, 0);
32 if (ret == MAP_FAILED)
33 return NULL;
35 return ret;
38 static void dump_maps(void)
40 struct map *m;
41 struct list_head *node;
43 output(2, "There are %d entries in the map table\n", num_mappings);
45 list_for_each(node, &maps->list) {
46 m = (struct map *) node;
47 output(2, " start: %p name: %s\n", m->ptr, m->name);
51 static void alloc_zero_map(int prot, const char *name)
53 struct map *newnode;
54 struct list_head *list;
55 unsigned long size = 0;
57 /* Pick a random sized mmap. */
58 switch (rand() % 4) {
59 case 0: size = page_size;
60 break;
61 case 1: size = 1024 * 1024;
62 break;
63 case 2: size = 2 * (1024 * 1024);
64 break;
65 case 3: size = 4 * (1024 * 1024);
66 break;
67 default:
68 break;
71 /* page_size * 2, so we have a guard page afterwards.
72 * This is necessary for when we want to test page boundaries.
73 * see end of _get_address() for details.
75 size *= 2;
77 newnode = zmalloc(sizeof(struct map));
78 newnode->name = strdup(name);
79 newnode->size = size;
80 newnode->ptr = mmap(NULL, size, prot, MAP_ANONYMOUS | MAP_SHARED, 0, 0);
81 if (newnode->ptr == MAP_FAILED) {
82 outputerr("mmap failure\n");
83 exit(EXIT_FAILURE);
86 newnode->name = malloc(80);
87 if (!newnode->name) {
88 outputerr("malloc() failed in %s().", __func__);
89 exit(EXIT_FAILURE);
92 sprintf(newnode->name, "anon(%s)", name);
94 num_mappings++;
96 list = &maps->list;
97 list_add_tail(&newnode->list, list);
99 output(2, "mapping[%d]: (zeropage %s) %p (%lu bytes)\n",
100 num_mappings - 1, name, newnode->ptr, size);
103 void setup_maps(void)
105 maps = zmalloc(sizeof(struct map));
106 INIT_LIST_HEAD(&maps->list);
108 alloc_zero_map(PROT_READ | PROT_WRITE, "PROT_READ | PROT_WRITE");
109 alloc_zero_map(PROT_READ, "PROT_READ");
110 alloc_zero_map(PROT_WRITE, "PROT_WRITE");
112 dump_maps();
115 /* Walk the list, get the j'th element */
116 void * get_map(void)
118 struct map *m;
119 struct list_head *node;
120 unsigned int i, j = 0;
122 i = rand() % num_mappings;
124 list_for_each(node, &maps->list) {
125 m = (struct map *) node;
127 if (i == j)
128 return m->ptr;
129 j++;
131 return 0;
134 void destroy_maps(void)
136 struct map *m = maps;
138 while (!list_empty(&maps->list)) {
139 m = maps;
141 munmap(m->ptr, m->size);
142 free(m->name);
144 maps = (struct map *) m->list.next;
146 list_del(&m->list);
147 free(m);
149 num_mappings = 0;
152 void init_buffers(void)
154 unsigned int i;
156 output(2, "shm is at %p\n", shm);
158 page_zeros = memalign(page_size, page_size * 2);
159 if (!page_zeros)
160 exit(EXIT_FAILURE);
161 memset(page_zeros, 0, page_size);
162 output(2, "page_zeros @ %p\n", page_zeros);
164 page_0xff = memalign(page_size, page_size * 2);
165 if (!page_0xff)
166 exit(EXIT_FAILURE);
167 memset(page_0xff, 0xff, page_size);
168 output(2, "page_0xff @ %p\n", page_0xff);
170 page_rand = memalign(page_size, page_size * 2);
171 if (!page_rand)
172 exit(EXIT_FAILURE);
173 memset(page_rand, 0x55, page_size); /* overwritten below */
174 output(2, "page_rand @ %p\n", page_rand);
176 page_allocs = memalign(page_size, page_size * 2);
177 if (!page_allocs)
178 exit(EXIT_FAILURE);
179 memset(page_allocs, 0xff, page_size);
180 output(2, "page_allocs @ %p\n", page_allocs);
182 for (i = 0; i < (page_size / sizeof(unsigned long *)); i++)
183 page_allocs[i] = (unsigned long) malloc(page_size);
185 setup_maps();
187 // generate_random_page may end up using maps, so has to be last.
188 generate_random_page(page_rand);