Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

mmap affects sbrk #124

Open
xxuejie opened this issue Sep 10, 2018 · 0 comments
Open

mmap affects sbrk #124

xxuejie opened this issue Sep 10, 2018 · 0 comments

Comments

@xxuejie
Copy link

xxuejie commented Sep 10, 2018

Hi there,

I was reading mmap code here, and I found that mmap actually uses __vm_alloc when MAP_FIXED is not used. However __vm_alloc would search for pages starting at current.brk, the result of this, is that mmap calls would affect brk_max, which then limits the size of memory brk can change.

So the following program:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stddef.h>
#include <malloc.h>
#include <machine/syscall.h>

#define PAGE_SIZE (1 << 12)

#define PROT_NONE 0
#define PROT_READ 1
#define PROT_WRITE 2
#define PROT_EXEC 4

#define MAP_PRIVATE 0x2
#define MAP_FIXED 0x10
#define MAP_ANONYMOUS 0x20
#define MAP_POPULATE 0x8000

uintptr_t mmap(uintptr_t addr, size_t length, int prot, int flags, int fd, off_t offset)
{
  return syscall_errno(222, addr, length, prot, flags, fd, offset);
}

size_t brk(size_t pos)
{
  return syscall_errno(214, pos, 0, 0, 0, 0, 0);
}

int main(int argc, char *argv[]) {
  size_t initial_brk = brk(0);
  printf("Initial brk: 0x%08X\n", initial_brk);

  void *buf = malloc(1000);
  printf("Malloc result: 0x%08X\n", (uintptr_t) buf);

  void *ptr = (void *) mmap(0, 1000, PROT_WRITE | PROT_READ | PROT_EXEC, MAP_PRIVATE | MAP_ANONYMOUS, -1, 0);
  printf("mmap result: 0x%08X\n", ptr);

  buf = malloc(1000);
  printf("Malloc result: 0x%08X\n", (uintptr_t) buf);

  buf = malloc(1000);
  printf("Malloc result: 0x%08X\n", (uintptr_t) buf);

  buf = malloc(1000);
  printf("Malloc result: 0x%08X\n", (uintptr_t) buf);

  buf = malloc(1000);
  printf("Malloc result: 0x%08X\n", (uintptr_t) buf);

  return 0;
}

Would generate the following result:

Initial brk: 0x0001DFF8
Malloc result: 0x0001E408
mmap result: 0x0001F000
Malloc result: 0x0001E7F8
Malloc result: 0x0001EBE8
Malloc result: 0x00000000
Malloc result: 0x00000000

I'm testing this on rv32imac target but I think the result is the similar across all targets. My question is: is this expected behavior? Does this mean we have to be extra cautious when using mmap?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant