{"id":2452,"date":"2015-07-29T16:39:06","date_gmt":"2015-07-29T13:39:06","guid":{"rendered":"https:\/\/upcloud.com\/global\/us\/resources\/tutorials\/troubleshoot-linux-memory-issues\/"},"modified":"2026-04-23T14:32:31","modified_gmt":"2026-04-23T13:32:31","slug":"troubleshoot-linux-memory-issues","status":"publish","type":"tutorial","link":"https:\/\/upcloud.com\/global\/resources\/tutorials\/troubleshoot-linux-memory-issues\/","title":{"rendered":"How to troubleshoot Linux server memory issues"},"content":{"rendered":"\n<p class=\"wp-block-paragraph\">Some unexpected behaviour on the server side may sometimes be caused by system resource limitations. Linux by its design aims to use all of the available physical memory as efficiently as possible, in practice, the Linux kernel follows a basic rule that a page of free RAM is wasted RAM. The system holds a lot more in RAM than just application data, most importantly mirrored data from storage drives for faster access. This debugging guide aims to explain how to identify how much of the resources are actually being used and how to recognise real resource outage issues.<\/p>\n\n\n\n\n\n<h2 class=\"wp-block-heading\">Process stopped unexpectedly<\/h2>\n\n\n\n<p class=\"wp-block-paragraph\">Suddenly killed tasks are often the result of the system running out of memory, which is when the so-called Out-of-memory (OOM) killer steps in. If a task gets killed to save memory, it gets logged into various log files stored at \/var\/log\/<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">You can search the logs for messages of out-of-memory alerts.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">sudo grep -i -r 'out of memory' \/var\/log\/<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Grep goes through all logs under the directory and, therefore, will show at least the just ran command itself from the \/var\/log\/auth.log. Actual log marks of OOM killed processes would look something like the following.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">kernel: Out of memory: Kill process 9163 (mysqld) score 511 or sacrifice child<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">The log note here shows the process killed was mysqld with pid 9163 and an OOM score of 511 at the time it was killed. Your log messages may vary depending on Linux distribution and system configuration.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">If, for example, a process crucial to your web application was killed as a result of an out-of-memory situation, you have a couple of options: reduce the amount of memory asked by the process, disallow processes to overcommit memory, or simply add more memory to your server configuration.<\/p>\n\n\n\n<div class=\"wp-block-buttons is-layout-flex wp-block-buttons-is-layout-flex\">\n<div class=\"wp-block-button\"><a class=\"wp-block-button__link wp-element-button\" href=\"https:\/\/signup.upcloud.com\/\">Try UpCloud for free!<\/a><\/div>\n<\/div>\n\n\n\n<h2 class=\"wp-block-heading\">Current resource usage<\/h2>\n\n\n\n<p class=\"wp-block-paragraph\">Linux comes with a few handy tools for tracking processes that can help identify possible resource outages. The command below, for example, can track memory usage.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">free -h<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">The command prints out current memory statistics, for example in a 1 GB system the output is something along the lines of the example underneath.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">                   total   used    free    shared  buffers cached\nMem:               993M    738M    255M    5.7M    64M     439M\n-\/+ buffers\/cache: 234M    759M\nSwap:              0B      0B      0B<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">It is important to distinguish between application-used memory, buffers, and caches here. On the Mem line of the output, it would appear that nearly 75% of our RAM is in use, but over half of the used memory is occupied by cached data.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">The difference is that while applications reserve memory for their own use, the cache is simply commonly used hard drive data that the kernel stores temporarily in RAM space for faster access, which on the application level is considered free memory.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Keeping that in mind, it\u2019s easier to understand why used and free memory are listed twice. On the second line, the actual memory usage is conveniently calculated when taking into account the amount of memory occupied by buffers and cache.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">In this example, the system uses only 234MB of the total available 993MB, and no process is in danger of being killed to save resources.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Another useful tool for memory monitoring is \u2018top\u2019, which displays useful, continuously updated information about processes\u2019 memory and CPU usage, runtime and other statistics. This is particularly useful for identifying exhaustive tasks for resources.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">top<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">You can scroll the list using the Page Up and Page Down buttons on your keyboard. The program runs in the foreground until canceled by pressing \u2018q\u2019 to quit. The resource usage is shown in percentages, giving an easy overview of your system\u2019s workload.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">top - 17:33:10 up 6 days,  1:22,  2 users,  load average: 0.00, 0.01, 0.05\nTasks:  72 total,   2 running,  70 sleeping,   0 stopped,   0 zombie\n%Cpu(s):  0.3 us,  0.0 sy,  0.0 ni, 99.7 id,  0.0 wa,  0.0 hi,  0.0 si,  0.0 st\nKiB Mem:   1017800 total,   722776 used,   295024 free,    66264 buffers\nKiB Swap:        0 total,        0 used,        0 free.   484748 cached Mem\n\n  PID USER      PR  NI    VIRT    RES    SHR S %CPU %MEM     TIME+ COMMAND\n    1 root      20   0   33448   2784   1448 S  0.0  0.3   0:02.91 init\n    2 root      20   0       0      0      0 S  0.0  0.0   0:00.00 kthreadd\n    3 root      20   0       0      0      0 S  0.0  0.0   0:00.02 ksoftirqd\/0\n    5 root       0 -20       0      0      0 S  0.0  0.0   0:00.00 kworker\/0:0H\n    6 root      20   0       0      0      0 S  0.0  0.0   0:01.92 kworker\/u2:0\n    7 root      20   0       0      0      0 S  0.0  0.0   0:05.48 rcu_sched\n<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">In the example output shown above, the system is idle, and the memory usage is nominal.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Check if your process is at risk<\/h2>\n\n\n\n<p class=\"wp-block-paragraph\">If your server\u2019s memory is used up to the extent that it can threaten system stability, the Out-of-memory killer will choose which process to eliminate based on many variables, such as the amount of work done that would be lost and the total memory freed. Linux keeps a score for each running process, representing the likelihood of the process being killed in an OOM situation.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">This score is stored on file in \/proc\/&lt;pid&gt;\/oom_score, where pid is the identification number for the process you are looking into. The pid can be easily found using the following command.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">ps aux | grep &lt;process name&gt;<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">The command output when searching for &#8216;mysql&#8217;, for example, would be similar to the example below.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">mysql     5872  0.0  5.0 623912 51236 ?        Ssl  Jul16   2:42 \/usr\/sbin\/mysqld<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Here, the process ID is the first number on the row, 5872 in this case. It can then be used to obtain further information on this particular task.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">cat \/proc\/5872\/oom_score<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">The readout of this gives us a single numerical value for the chance of the OOM killer axing the process. The higher the number, the more likely the task is to be chosen if an out-of-memory situation should arise.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">If your important process has a very high OOM score, it may be wasting memory and should be looked into. However, a high OOM score, if the memory usage remains nominal, is no reason for concern. OOM killer can be disabled, but this is not recommended as it might cause unhandled exceptions in out-of-memory situations, possibly leading to a kernel panic or even a system halt.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Disable over commit<\/h2>\n\n\n\n<p class=\"wp-block-paragraph\">In major Linux distributions, the kernel allows processes to request more memory than is currently free in the system by default to improve memory utilization. This is based on the heuristic that processes never truly use all the memory they request. However, if your system is at risk of running out of memory and you wish to prevent losing tasks to OOM killer, it is possible to disallow memory overcommit.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">To change how the system handles overcommit calls, Linux has an application called \u2018sysctl\u2019 that is used to modify kernel parameters at runtime. You can list all sysctl-controlled parameters using the following.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">sudo sysctl -a<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">The particular parameters that control memory are very imaginatively named vm.overcommit_memory and vm.overcommit_ratio. To change the overcommit mode, use the below command.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">sudo sysctl -w vm.overcommit_memory=2<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">This parameter has 3 different values:<\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li>0 means \u201cEstimate if we have enough RAM\u201d<\/li>\n\n\n\n<li>1 equals \u201cAlways allow\u201d<\/li>\n\n\n\n<li>2 is used here tells the kernel to \u201cSay no if the system doesn\u2019t have the memory\u201d<\/li>\n<\/ul>\n\n\n\n<p class=\"wp-block-paragraph\">The important part of changing the overcommit mode is remembering to also change the overcommit_ratio. When overcommit_memory is set to 2, the committed address space is not permitted to exceed swap space plus this percentage of physical RAM. To be able to use all of the system\u2019s memory, use the next command.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">sudo sysctl -w vm.overcommit_ratio=100<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">These changes are applied immediately but will only persist until the next system reboot. To have the changes remain permanent, the same parameter values need to be added to sysctl.conf \u2013file. Open the configuration file for edit.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">sudo nano \/etc\/sysctl.conf<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Add the same lines to the end of the file.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">vm.overcommit_memory=2\nvm.overcommit_ratio=100<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Save the changes (ctrl + O) and exit (ctrl + X) the editor. Your server will read the configurations every time at boot up, and prevent applications from overcommitting memory.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Add more memory to your server<\/h2>\n\n\n\n<p class=\"wp-block-paragraph\">The safest and most future-proof option for solving out-of-memory issues is adding more memory to your system. In a traditional server environment, you would need to order new memory modules, wait for them to arrive, and install them into your system, but with cloud servers, all you have to do is increase the amount of RAM you wish to have available at your <a title=\"UpCloud Control Panel\" href=\"https:\/\/hub.upcloud.com\/\" target=\"_blank\" rel=\"noopener\">UpCloud Control Panel<\/a>.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Log in to your UpCloud control panel, browse to the Server Listing and open your server\u2019s details by clicking on its description. In the Server General Settings tab, there is a section on the right name CPU and Memory Settings. While your server is running, you will notice that these options are greyed out, this is because they may only be safely changed while the server is shut down.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Proceed by turning off your server with the Shutdown request option on the left of the same page, and click OK in the confirmation dialogue. It will usually take a moment for the server to shut down completely, but once it has the CPU and Memory Settings will become available without you having to refresh the page.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Now you will have two options to increase the amount of RAM in your system:<\/p>\n\n\n\n<ol class=\"wp-block-list\">\n<li>Select a larger preconfigured instance from the Configuration drop-down menu.<\/li>\n\n\n\n<li>Select the&nbsp;Custom configuration from the same box and then use the slider underneath.<\/li>\n<\/ol>\n\n\n\n<p class=\"wp-block-paragraph\">The slider allows you to select a value in increments of 1GB to change the RAM to the desired configuration. Changing your server\u2019s configuration also affects the pricing of your server. To see the corresponding prices to each preconfigured option or custom configuration, check the server configuration options at the <a title=\"Deploy a server\" rel=\"noopener\" href=\"https:\/\/hub.upcloud.com\/deploy\" target=\"_blank\">new server deployment<\/a>.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Once you\u2019ve selected the new server configuration, simply press the Update button on the right and the changes will be made immediately. Then you can start your server again with the increased RAM.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">If you selected a larger preconfigured option, refer to our <a href=\"https:\/\/upcloud.com\/global\/docs\/guides\/increasing-storage-size\/\" target=\"_blank\" rel=\"noreferrer noopener\">resizing storage guide<\/a> on how to allocate the newly added disk space.<\/p>\n","protected":false},"author":3,"featured_media":27309,"comment_status":"open","ping_status":"closed","template":"","community-category":[289],"class_list":["post-2452","tutorial","type-tutorial","status-publish","has-post-thumbnail","hentry"],"acf":[],"_links":{"self":[{"href":"https:\/\/upcloud.com\/global\/wp-json\/wp\/v2\/tutorial\/2452","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/upcloud.com\/global\/wp-json\/wp\/v2\/tutorial"}],"about":[{"href":"https:\/\/upcloud.com\/global\/wp-json\/wp\/v2\/types\/tutorial"}],"author":[{"embeddable":true,"href":"https:\/\/upcloud.com\/global\/wp-json\/wp\/v2\/users\/3"}],"replies":[{"embeddable":true,"href":"https:\/\/upcloud.com\/global\/wp-json\/wp\/v2\/comments?post=2452"}],"version-history":[{"count":1,"href":"https:\/\/upcloud.com\/global\/wp-json\/wp\/v2\/tutorial\/2452\/revisions"}],"predecessor-version":[{"id":6475,"href":"https:\/\/upcloud.com\/global\/wp-json\/wp\/v2\/tutorial\/2452\/revisions\/6475"}],"wp:attachment":[{"href":"https:\/\/upcloud.com\/global\/wp-json\/wp\/v2\/media?parent=2452"}],"wp:term":[{"taxonomy":"community-category","embeddable":true,"href":"https:\/\/upcloud.com\/global\/wp-json\/wp\/v2\/community-category?post=2452"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}