Limiting child process's memory usage with rlimit without affecting current process

1.8k Views Asked by At

I want to limit the memory usage of a child process using rlimit. Currently our code is as follows:

old_rlimit := get_rlimit()
set_rlimit(child_process_rlimit)
cmd.Start()
set_rlimit(old_rlimit)
cmd.Wait()

However, sometimes Golang runtime will report out of memory error at cmd.Start(). It seems that in cmd.Start() current process will allocate some memory, and if current memory usage is higher than child_process_rlimit, an error will be raised.

I want to know is there any way to limit the memory usage of child process without affecting current one?

1

There are 1 best solutions below

2
Marc On

You need to apply rlimit to the child process only rather than relying on rlimit inheritance. Your main blocker here is clearly spelled out in the setrlimit man page:

an unprivileged process may set only its soft limit to a value in the range from 0 up to the hard limit, and (irreversibly) lower its hard limit

The standard way to do this is through fork/exec, something along the lines of:

child_pid := fork()
if pid != 0 {
  // in child process
  setrlimit(...)
  execve(...)
}

If you don't want to do that, you still have a few options:

  • run as privileged user
  • cmd.Run a small wrapper (eg: bash ulimit -m ...) that calls the child process. note: -m is not honored by many systems.
  • call prlimit (linux-specific and no syscall wrapper. see this thread for details)