summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJames Bottomley <James.Bottomley@HansenPartnership.com>2020-04-17 15:10:39 -0700
committerJames Bottomley <James.Bottomley@HansenPartnership.com>2020-04-17 15:10:39 -0700
commitf00e31f8a7e180acd52b2fb86649509462622b9d (patch)
tree68693c92e6af1b807bb851fe4bb5f6e17e9f818c
parent41ff5cc4f9f360fab0a3fd696ca6aa266eb02cba (diff)
downloadsecret-memory-preloader-f00e31f8a7e180acd52b2fb86649509462622b9d.tar.gz
refactor in preparation for allocating multiple segments
-rw-r--r--preload.c80
1 files changed, 52 insertions, 28 deletions
diff --git a/preload.c b/preload.c
index c34f976..841ddbb 100644
--- a/preload.c
+++ b/preload.c
@@ -58,11 +58,11 @@ struct segptr {
};
struct malloc_state {
- struct segptr seg;
+ struct segptr *seg;
struct malloc_chunk free;
};
-static struct malloc_state *m;
+static struct malloc_state m;
static int in_use(struct malloc_chunk *c)
{
@@ -86,7 +86,7 @@ static struct segptr *chunk_to_segment(struct malloc_chunk *c)
{
struct segptr *sp;
- for (sp = &m->seg; sp != NULL; sp = sp->next)
+ for (sp = m.seg; sp != NULL; sp = sp->next)
if (sp->base <= (char *)c &&
(char *)c < sp->base + SEG_SIZE)
return sp;
@@ -113,6 +113,8 @@ static struct malloc_chunk *next_chunk(struct malloc_chunk *c)
struct segptr *seg = chunk_to_segment(c);
void *n = (char*)c + chunk_size(c);
+ ASSERT(seg != NULL);
+
ASSERT((char *)n > seg->base &&
(char *)n <= seg->base + SEG_SIZE);
if (n == seg->base + SEG_SIZE)
@@ -130,7 +132,7 @@ static struct malloc_chunk *prev_chunk(struct malloc_chunk *c)
static void link_free_chunk(struct malloc_chunk *c)
{
- struct malloc_chunk *f = &m->free;
+ struct malloc_chunk *f = &m.free;
struct malloc_chunk *b = f->bk;
c->fd = f;
@@ -152,35 +154,35 @@ static void unlink_free_chunk(struct malloc_chunk *c)
static void show_segment(void)
{
struct malloc_chunk *c;
+ struct segptr *seg;
+ int i;
if (!debug)
return;
- printf("SHOW SEGMENT\n");
- for (c = (struct malloc_chunk *)m->seg.base; c != NULL; c = next_chunk(c)) {
- printf("%p:%d:%d:%04x:%04x", c, in_use(c), prev_in_use(c),
- c->prev_foot, chunk_size(c));
- if (!in_use(c))
- printf(":%p:%p", c->fd, c->bk);
- printf("\n");
+ for (i = 0, seg = m.seg; seg != NULL; i++, seg = seg->next) {
+ printf("SHOW SEGMENT %i\n", i);
+ for (c = (struct malloc_chunk *)seg->base; c != NULL; c = next_chunk(c)) {
+ printf("%p:%d:%d:%04x:%04x", c, in_use(c), prev_in_use(c),
+ c->prev_foot, chunk_size(c));
+ if (!in_use(c))
+ printf(":%p:%p", c->fd, c->bk);
+ printf("\n");
+ }
}
-
printf("SHOW SEGMENT END\n");
}
-void __attribute__ ((constructor)) preload_setup(void)
+static int use_secret = 1;
+
+static void alloc_segment(void)
{
int fd;
int ret;
void *p;
+ struct segptr *seg, *sp, **psp;
+ const size_t ssize = pad_request(sizeof(*seg));
struct malloc_chunk *c;
- const size_t msize = pad_request(sizeof(*m));
- int use_secret = 1;
-
- if (getenv("MALLOC_DEBUG") != NULL)
- debug = 1;
- if (getenv("NO_SECRET_MEM") != NULL)
- use_secret = 0;
if (use_secret)
fd = memfd_create("secure", MFD_CLOEXEC|MFD_SECRET);
@@ -198,28 +200,50 @@ void __attribute__ ((constructor)) preload_setup(void)
p = mmap(NULL, SEG_SIZE, PROT_READ|PROT_WRITE, MAP_SHARED, fd, 0);
check(p == MAP_FAILED, "mmap");
+ close(fd);
DEBUG("initial malloc at 0x%p-0x%p\n", p, p+SEG_SIZE);
c = p;
- m = chunk2mem(c);
- memset(m, 0, sizeof(*m));
- c->head = msize | CINUSE_BIT | PINUSE_BIT;
- m->seg.base = p;
+ seg = chunk2mem(c);
+ memset(seg, 0, sizeof(*seg));
+ seg->base = p;
+ c->head = ssize | CINUSE_BIT | PINUSE_BIT;
+ c->prev_foot = 0;
+
+ if (m.seg == NULL) {
+ m.seg = seg;
+ } else {
+ for (sp = m.seg; sp->next == NULL; sp = sp->next)
+ ;
+ sp->next = seg;
+ }
c = next_chunk(c);
+ printf("NEXT CHUNK %p\n", c);
c->head = (size_t)(((char *)p + SEG_SIZE) - (char *)c) | PINUSE_BIT;
- c->prev_foot = msize;
+ c->prev_foot = ssize;
DEBUG("next chunk at 0x%p, head=%x, prev=%x\n", c, chunk_size(c), c->prev_foot);
- m->free.fd = &m->free;
- m->free.bk = &m->free;
link_free_chunk(c);
}
+void __attribute__ ((constructor)) preload_setup(void)
+{
+ if (getenv("MALLOC_DEBUG") != NULL)
+ debug = 1;
+ if (getenv("NO_SECRET_MEM") != NULL)
+ use_secret = 0;
+
+ m.free.fd = &m.free;
+ m.free.bk = &m.free;
+ m.seg = NULL;
+ alloc_segment();
+}
+
static struct malloc_chunk *find_free(size_t size)
{
struct malloc_chunk *c, *found = NULL;
- for (c = m->free.fd; c != &m->free; c = c->fd) {
+ for (c = m.free.fd; c != &m.free; c = c->fd) {
if (chunk_size(c) < size)
continue;
if (found && chunk_size(found) < chunk_size(c))