Limiting process memory/CPU usage on linux
I know we can adjust scheduling priority by using the nice command. However, the man page doesn’t say whether it will limit both CPU and memory or only CPU (and in any case, it can’t be used to specify absolute limits). Is there a way to run a process and limit its memory usage to say «X» MB and CPU usage to say «Y» Mhz in Linux?
Do you really want to limit CPU to so given clock or do you want to limit maximum CPU usage and still allow CPU clock to be automatically adjusted by the kernel? Note that CPUs cannot run lesser priority tasks with lower clock than higher priority tasks in parallel.
3 Answers 3
You might want to investigate cgroups as well as the older (obsolete) ulimit.
Linux specific answer:
For historical systems running ulimit -m $LIMIT_IN_KB would have been the correct answer. Nowadays you have to use cgroups and cgexec or systemd-run .
However, for systems that are still transitioning to systemd there does not seem to be any solution that does not require setting up pre-made configuration for each limit you wish to use. This is because such systems (e.g. Debian/Ubuntu) still use «hybrid hierachy cgroups» and systemd supports setting memory limits with newer «unified hierarchy cgroups» only. If your Linux distribution is already running systemd with unified hierarchy cgroups then running a given user mode process with specific limits should work like this
systemd-run --user --pipe -p MemoryMax=42M -p CPUWeight=10 [command-to-run . ]
systemd-run --user --scope -p MemoryMax=42M -p CPUWeight=10 [command-to-run . ]
For possible parameters, see man systemd.resource-control .
If I’ve understood correctly, setting CPUWeight instructs the kernel how much CPU you want to give if CPU is fully tasked and defaults to 100 , lower values mean less CPU time if multiple processes compete for CPU time. It will not limit CPU usage if CPU is utilized less than 100% which is usually a good thing. If you truly want to force the process to use less than a single core even when the machine is idle, you can set e.g. CPUQuota=10% to force process to use up to 10% of single core. If you set CPUQuota=200% it means the process can use up to 2 cores on average (but without CPU binding it can use some of its time on more CPUs).
Update (year 2021): It seems that
systemd-run --user --pty -p MemoryMax=42M -p CPUWeight=10 .
should work if you’re running version of systemd including a fix to bug https://github.com/systemd/systemd/issues/9512 – in practice, you need fixes listed here: https://github.com/systemd/systemd/pull/10894
If your system is lacking those fixes, the command
systemd-run --user --pty -p MemoryMax=42M -p CPUWeight=10 .
appears to work but the memory limits are not actually enforced.
In reality, it seems that Ubuntu 20.04 LTS does not contain required fixes. Following should fail:
$ systemd-run --user --pty -p MemoryMax=42M -p MemorySwapMax=50M -p CPUWeight=10 stress -t 10 --vm-keep --vm-bytes 10m -m 20
because the command stress is expected to require slightly more than 200 MB of RAM but memory limits are set lower. According to bug https://github.com/systemd/systemd/issues/10581 Poettering says that this should work if distro is using cgroupsv2 , whatever it means in practice.
I don’t know a distro that implements user mode cgroup limits correctly. As a result, you need root to configure the limits.
Linux cpu limit usage
NAME
cpulimit -- limits the CPU usage of a process
SYNOPSIS
cpulimit [TARGET] [OPTIONS. ] [ -- PROGRAM]
DESCRIPTION
TARGET must be exactly one of these: -p, --pid=N pid of the process -e, --exe=FILE name of the executable program file -P, --path=PATH absolute path name of the executable program file OPTIONS -b, --background run cpulimit in the background, freeing up the terminal -c, --cpu specify the number of CPU cores available. Usually this is detected for us. -l, --limit=N percentage of CPU allowed from 1 up. Usually 1 - 100, but can be higher on multi- core CPUs. (mandatory) -q, --quiet Runs in quiet mode, avoids writing update messages to console. -k, --kill kill target process instead of throttling its CPU usage -r, --restore restore a process killed using the -k flag. -s, --signal send an alternative signal to the watched process when we exit. Default is SIGCONT. -v, --verbose show control statistics -z, --lazy exit if there is no suitable target process, or if it dies -- This is the final CPUlimit option. All following options are for another program we will launch. -h, --help display this help and exit
EXAMPLES
Assuming you have started `foo --bar` and you find out with top(1) or ps(1) that this process uses all your CPU time you can either # cpulimit -e foo -l 50 limits the CPU usage of the process by acting on the executable program file (note: the argument "--bar" is omitted) # cpulimit -p 1234 -l 50 limits the CPU usage of the process by acting on its PID, as shown by ps(1) # cpulimit -P /usr/bin/foo -l 50 same as -e but uses the absolute path name # /usr/bin/someapp # cpulimit -p $! -l 25 -b Useful for scripts where you want to throttle the last command run. # cpulimit -l 20 firefox Launch Firefox web browser and limit its CPU usage to 20% # cpulimit -l 25 -- firefox -private Launch Firefox web browser in private mode and limit its CPU usage to 25% # cpulimit -c 2 -p 12345 -l 25 The -c flag sets the number of CPU cores the program thinks are available. Usually this is detected for us, but can be over-ridden. # cpulimit -l 20 -k firefox Launch the Firefox program and kill it if the process goes over 20% CPU usage. # cpulimit -l 20 -p 1234 -s SIGTERM Throttle process 1234 at 20% CPU usage. If cpulimit is forced to exit, it sends the watched process the SIGTERM signal.
NOTES
• cpulimit always sends the SIGSTOP and SIGCONT signals to a process, both to verify that it can control it and to limit the average amount of CPU it consumes. This can result in misleading (annoying) job control messages that indicate that the job has been stopped (when actually it was, but immediately restarted). This can also cause issues with interactive shells that detect or otherwise depend on SIGSTOP/SIGCONT. For example, you may place a job in the foreground, only to see it immediately stopped and restarted in the background. (See also http://bugs.debian.org/558763>.) • When invoked with the -e or -P options, cpulimit looks for any process under /proc with a name that matches the process name argument given. Furthermore, it uses the first instance of the process found. To control a specific instance of a process, use the -p option and provide a PID. • The current version of cpulimit assumes the kernel HZ value 100.
AUTHOR
This manpage was written for the Debian project by gregor herrmann gregoa@debian.org> but may be used by others.
© 2019 Canonical Ltd. Ubuntu and Canonical are registered trademarks of Canonical Ltd.
Limit CPU Usage of a Process in Linux with CPULimit Tool
In an earlier post, we’ve explained CPUTool for limiting and controlling CPU utilization of any process in Linux. It allows a system administrator to interrupt execution of a process (or process group) if the CPU/system load goes beyond a defined threshold. Here, we will learn how to use a similar tool called cpulimit.
Cpulimit is used to restrict the CPU usage of a process in the same way as CPUTool, however, it offers more usage options compared to its counterpart. One important difference is that cpulimit doesn’t manage system load unlike cputool.
Install CPULimit to Limit CPU Usage Of a Process in Linux
CPULimit is available to install from default software repositories of Debian/Ubuntu and its derivatives using a package management tool.
$ sudo apt install cpulimit
In RHEL/CentOS and Fedora, you need to first enable EPEL repository and then install cpulimit as shown.
# yum install epel-release
# yum install cpulimit
Limiting Process CPU Usage With CUPLimit
In this sub section, we’ll explain how cpulimit works. First, let’s run a command (same dd command we looked at while covering cputool) which should result into a high CPU percentage, in the background (note that the process PID is printed out after running the command).
$ dd if=/dev/zero of=/dev/null & [1] 17918
Next, we can use the top or glances tools which output the actual frequently updated state of a running Linux system, to watch the CPU usage of the command above.
Looking at the output above, we can see that the dd process is utilizing the highest percentage of CPU time 100.0%.
But we can limit this using cputlimit as follows. The —pid or -p option is used to specify the PID and —limit or -l is used to set a usage percentage for a process.
The command below will limit the dd command (PID 17918) to 50% use of one CPU core.
$ sudo cpulimit --pid 17918 --limit 50 Process 17918 detected
Once we run cpulimit, we can view the current CPU usage for the dd command with top or glances. From the output, the value ranges from (51.5%-55.0% or slightly beyond).
We can throttle its CPU usage for a second time as follows, this time lowering the percentage further as follows:
$ sudo cpulimit --pid 17918 --limit 20 Process 17918 detected
As we did before, we can run top or glances to view the new CPU usage for the process, which will range from 20%-25.0% or slightly beyond this.
Note: The shell becomes un-interactive – doesn’t expect any user input when cpulimit is running. To kill it (which should stop the CPU usage limitation operation), press [Ctrl + C] .
To run cpulimit as a background process, use the —background or -b switch, freeing up the terminal.
$ sudo cpulimit --pid 17918 --limit 20 --background
To specify the number of CPU cores present on the system, use the —cpu or -c flag (this is normally detected automatically).
$ sudo cpulimit --pid 17918 --limit 20 --cpu 4
Rather than limit a process’s CPU usage, we can kill it with the —kill or -k option. The default is signal sent to the process is SIGCONT, but to send a different signal, use the —signal or -s flag.
$ sudo cpulimit --pid 17918 --limit 20 --kill
To exit if there is no suitable target process, or in case it dies, include the -z or —lazy like this.
$ sudo cpulimit --pid 17918 --limit 20 --kill --lazy
For additional information and usage options, view the cpulimit man page.
Do check out the following useful guides for finding CPU info and CPU/system performance monitoring.
In comparison, after testing CPUTool and CPULimit, we noticed that the former offers a more effective and reliable “process CPU usage limitation” functionality.
This is according to the percentage range of CPU usage observed after running both tools against a given process. Try out both tools and add your thoughts to this article using the feedback form below.