Linux ulimit command
Содержание:
init.d
The different implementations of init.d vary, but they have known drawbacks. For example, init.d starts everything sequentially. This means a new process has to wait if another has already started. This makes the startup process on multi-core machine slow. Another drawback related to our topic is that daemons started by init.d inherit OS limits from the root user. If a program needs to be run by another user, the switch needs to happen in the startup script itself. But the order of option files that such users read can be different, depending on if they are logged in via the ssh, su or sudo commands.
Percona Server for MySQL
Before version 5.7, Percona Server for MySQL had a different startup sequence:
- <Perform another job>
- Start mysqld_safe as root and pass option —user=mysql to it: «${PERCONA_PREFIX}»binmysqld_safe>devnull2>&1&
With this sequence, you only need to set a hard limit for a mysql user in the file etcsecuritylimits.conf, and mysqld_safe will do the rest.
In version 5.7, Percona Server for MySQL backported the startup sequence from MySQL Server. Since then, setting a hard limit on the number of open files for mysql users in etcsecuritylimits.conf is not enough. You also need to have a row session required pam_limits.so in the file etcpam.dcommon-session. This is needed because the startup sequence for mysql users changed due to the design of init.d.
BUGS top
In older Linux kernels, the SIGXCPU and SIGKILL signals delivered when a process encountered the soft and hard RLIMIT_CPU limits were delivered one (CPU) second later than they should have been. This was fixed in kernel 2.6.8. In 2.6.x kernels before 2.6.17, a RLIMIT_CPU limit of 0 is wrongly treated as "no limit" (like RLIM_INFINITY). Since Linux 2.6.17, setting a limit of 0 does have an effect, but is actually treated as a limit of 1 second. A kernel bug means that RLIMIT_RTPRIO does not work in kernel 2.6.12; the problem is fixed in kernel 2.6.13. In kernel 2.6.12, there was an off-by-one mismatch between the priority ranges returned by getpriority(2) and RLIMIT_NICE. This had the effect that the actual ceiling for the nice value was calculated as 19 - rlim_cur. This was fixed in kernel 2.6.13. Since Linux 2.6.12, if a process reaches its soft RLIMIT_CPU limit and has a handler installed for SIGXCPU, then, in addition to invoking the signal handler, the kernel increases the soft limit by one second. This behavior repeats if the process continues to consume CPU time, until the hard limit is reached, at which point the process is killed. Other implementations do not change the RLIMIT_CPU soft limit in this manner, and the Linux behavior is probably not standards conformant; portable applications should avoid relying on this Linux-specific behavior. The Linux-specific RLIMIT_RTTIME limit exhibits the same behavior when the soft limit is encountered. Kernels before 2.4.22 did not diagnose the error EINVAL for setrlimit() when rlim->rlim_cur was greater than rlim->rlim_max. Linux doesn't return an error when an attempt to set RLIMIT_CPU has failed, for compatibility reasons. Representation of "large" resource limit values on 32-bit platforms The glibc getrlimit() and setrlimit() wrapper functions use a 64-bit rlim_t data type, even on 32-bit platforms. However, the rlim_t data type used in the getrlimit() and setrlimit() system calls is a (32-bit) unsigned long. Furthermore, in Linux, the kernel represents resource limits on 32-bit platforms as unsigned long. However, a 32-bit data type is not wide enough. The most pertinent limit here is RLIMIT_FSIZE, which specifies the maximum size to which a file can grow: to be useful, this limit must be represented using a type that is as wide as the type used to represent file offsets—that is, as wide as a 64-bit off_t (assuming a program compiled with _FILE_OFFSET_BITS=64). To work around this kernel limitation, if a program tried to set a resource limit to a value larger than can be represented in a 32-bit unsigned long, then the glibc setrlimit() wrapper function silently converted the limit value to RLIM_INFINITY. In other words, the requested resource limit setting was silently ignored. Since version 2.13, glibc works around the limitations of the getrlimit() and setrlimit() system calls by implementing setrlimit() and getrlimit() as wrapper functions that call prlimit().
COLOPHON top
This page is part of the util-linux (a random collection of Linux utilities) project. Information about the project can be found at ⟨https://www.kernel.org/pub/linux/utils/util-linux/⟩. If you have a bug report for this manual page, send it to util-linux@vger.kernel.org. This page was obtained from the project's upstream Git repository ⟨git://git.kernel.org/pub/scm/utils/util-linux/util-linux.git⟩ on 2020-08-13. (At that time, the date of the most recent commit that was found in the repository was 2020-08-12.) If you discover any rendering problems in this HTML version of the page, or you believe there is a better or more up-to-date source for the page, or you have corrections or improvements to the information in this COLOPHON (which is not part of the original manual page), send a mail to man-pages@man7.org util-linux July 2014 PRLIMIT(1)
Pages that refer to this page:
getrlimit(2),
prlimit(2),
prlimit64(2),
setrlimit(2),
ugetrlimit(2),
vlimit(3),
cgroups(7)
ERRORS top
EFAULT A pointer argument points to a location outside the accessible address space. EINVAL The value specified in resource is not valid; or, for setrlimit() or prlimit(): rlim->rlim_cur was greater than rlim->rlim_max. EPERM An unprivileged process tried to raise the hard limit; the CAP_SYS_RESOURCE capability is required to do this. EPERM The caller tried to increase the hard RLIMIT_NOFILE limit above the maximum defined by /proc/sys/fs/nr_open (see proc(5)) EPERM (prlimit()) The calling process did not have permission to set limits for the process specified by pid. ESRCH Could not find a process with the ID specified in pid.
Using ulimit in Linux
Here’s the syntax for ulimit command:
Display all limits for any user
You can display all kind of limits for a specified user in this manner:
The flag will display all options and their configuration for your specific user name.
If you omit the user_name, it shows limits for you. Let me show you the limits set up for me by default:
Your default values may be different than mine, of course. This view displays a description, the assigned flag (that can be used for changing the limits), and the configuration.
Display Hard and Soft Limits
It is also possible to see either of these respective limits with a flag.
To display soft limits, use option -S:
To display hard limits, use option -H:
It is more useful to combine these with specific flags from above. So if you want to check the hard limit on the maximum number of user processes, you would type:
Change the limits (temporarily)
Now, let’s change that value to 31500 for demonstration purposes and check the hard limit again.
It is worth noting that any changes your priviliege allows you will only be temporarily written and affect your current shell.
To confirm this, I exited my shell and created a new terminal and got the original default value.
The next section shows how to make the changes permanent.
Making permanent changes to ulimit
As I mentioned in the beginning of the article, ulimit is governed by /etc/security/limits.conf. If you want to make any permanent changes to the ulimits of any user, you will have to make changes to the security file as root.
When editing you need to include these four elements:
Here is the text I appended to the file to set the hard limit on the number of processes for user christoper (i.e. my own account):
Keep in mind that it is a best practice not to enable the root account unless you are fully aware of the potential consequences. I’ve done this on a virtual machine so you don’t have to do it yourself.
As you can see, the limit for ‘christopher’ was changed to 20000.
How do you know what keyword to use for editing the /etc/security/limits.conf file? Well, here is a table that includes possible item keywords and their descriptions:
Item Keyword | Description |
---|---|
core | limits the core file size (KB) |
data | max data size (KB) |
fsize | maximum filesize (KB) |
memlock | max locked-in-memory address space (KB) |
nofile | max number of open file descriptors |
rss | max resident set size (KB) |
stack | max stack size (KB) |
cpu | max CPU time (MIN) |
nproc | max number of processes |
as | address space limit (KB) |
maxlogins | max number of logins for this user |
maxsyslogins | max number of logins on the system |
priority | the priority to run user process with |
locks | max number of file locks the user can hold |
sigpending | max number of pending signals |
msgqueue | – max memory used by POSIX message queues (bytes) |
nice | max nice priority allowed to raise to values: |
rtprio | max realtime priority |
chroot | change root to directory (Debian-specific) |
Limit Type | Description |
---|---|
hard | hard limit |
soft | soft limit |
– | both hard and soft limit |
Change ulimit for groups
Changing a group policy is very similar to what you saw in the previous section but you will include an symbol before the name of the group.
Here’s an example where I set the maximum number of logins for the group student is 4 by editing the /etc/security/limits.conf file:
Conclusion
I hope you liked this quick primer on ulimit Linux command.
If you have any comments or questions, leave them below. If you have any suggestions for topics you’d like to see covered, feel free to leave those as well.
Как проверить все открытые файлы пользователем или процессом в Linux
В некоторых ситуациях на Linux могут возникать ошибки, связанные с превышением лимита использования файловых дескрипторов.
Эти лимиты накладываются как самим ядром Linux, так и его программными модулями, например PAM.
Лимит ядра Linux
Узнать текущее значение максимального количества файловых дескрипторов, определяемое ядром Linux можно командой:
# cat /proc/sys/fs/file-max
Этот лимит может быть изменён без перезагрузки системы (начинает действовать сразу и действует до перезагрузки):
# echo "1221724" > /proc/sys/fs/file-max
Чтобы требуемое значение использовалось постоянно, то есть действовало и после перезагрузки, его необходимо определить в конфиг.файле :
- sysclt.conf
-
... fs.file-max=1221724 ...
Методика подсчёта открытых файлов
Для получения информации о количестве всех открытых файлов всеми процессами в Linux некоторые «знатоки» предлагают использовать команду типа
# lsof | wc -l
Однако такая команда показывает гораздо большее значение, чем всего открыто файлов в системе на данный момент на самом деле. Это связано с тем, что по несколько раз в подсчёт попадают одни и теже открытые файлы, используемые разными процессами.
Поэтому проще для получения общего числа открытых файлов использовать данные ядра Linux
# cat /proc/sys/fs/file-nr
Первое число — общее количество занятых/используемых на данный момент времени файловых дескрипторов.
Второе число — количество выделенных процессам, но не используемых в данный момент дескрипторов.
Третье число — максимальное количество открытых дескрипторов
Примеры получения данных
Получить список TOP-20 процессов с самым большим количеством открытых файловых дескрипторов:
# for x in `ps -eF| awk '{ print $2 }'`; \ do echo `ls /proc/$x/fd 2> /dev/null | \ wc -l` $x `cat /proc/$x/cmdline 2> /dev/null`; \ done | sort -n -r | head -n 20
Подсчитать количество открытых файлов в разрезе процессов (в первой колонке будет выведен PID процесса, во второй количество открытых файлов этим процессом):
# ps aux | sed 1d | awk \ '{print "fd_count=$(lsof -p " $2 " | wc -l) && echo " $2 " $fd_count"}' | \ xargs -I {} bash -c {}
Посмотреть открытые файловые дескрипторы во всех процессах для отдельно взятого пользователя, например «apache»
# lsof -u apache
Подсчитать количество открытых файлов в каждом процессе для отдельно взятого пользователя:
# lsof -u apache | awk '{print $2}' | sort | uniq -c | sort -n
Тоже самое, только в реальном режиме времени:
# watch 'lsof -u vdsm | awk '\''{print $2}'\'' | sort | uniq -c | sort -n'
Посмотреть открыте файловые дескриптры для отдельно взятого процесса (по PID процесса):
# lsof -p 9189
Подсчитать количество файловых дескриптров для отдельно взятого процесса:
# lsof -p 9189 | wc -l
Дополнительные источники информации:
Блог Дениса Тулякова — Количество открытых файлов, сокетов
Проверено на следующих конфигурациях:
Версия ОС |
---|
Debian GNU/Linux 8.10 (jessie) |
Автор первичной редакции:Алексей Максимов
Время публикации: 09.06.2018 11:18
Ошибка too many open files Linux
Дословно эта ошибка означает, что программа открыла слишком много файлов и больше ей открывать нельзя. В Linux установлены жёсткие ограничения на количество открываемых файлов для каждого процесса и пользователя.
Посмотреть, сколько файлов можно открыть в вашей файловой системе, можно, выполнив команду:
Посмотреть текущие ограничения количества открытых файлов для пользователя можно командой:
Утилита ulimit возвращает два вида ограничений — hard и soft. Ограничение soft вы можете менять в любую сторону, пока оно не превышает hard. Ограничение hard можно менять только в меньшую сторону от имени обычного пользователя. От имени суперпользователя можно менять оба вида ограничений так, как нужно. По умолчанию отображаются soft-ограничения:
Чтобы вывести hard, используйте опцию -H:
Вы можете изменить ограничение, просто передав в ulimit новое значение:
Но поскольку hard-ограничение составляет 4000, то установить лимит больше этого значения вы не сможете. Чтобы изменить настройки ограничений для пользователя на постоянной основе, нужно настроить файл /etc/security/limits.conf. Синтаксис у него такой:
имя_пользователя тип_ограничения название_ограничения значение
Вместо имени пользователя можно использовать звездочку, чтобы изменения применялись ко всем пользователям в системе. Тип ограничения может быть soft или hard. Название — в нашем случае нужно nofile. И последний пункт — нужное значение. Установим максимум — 1617596.
Нужно установить значение для soft и hard параметра, если вы хотите, чтобы изменения вступили в силу. Также убедитесь, что в файле /etc/pam.d/common-session есть такая строчка:
Если её нет, добавьте в конец. Она нужна, чтобы ваши ограничения загружались при авторизации пользователя.
Если вам нужно настроить ограничения только для определенного сервиса, например Apache или Elasticsearch, то для этого не обязательно менять все настройки в системе. Вы можете сделать это с помощью systemctl. Просто выполните:
И добавьте в открывшейся файл такие строки:
Здесь мы устанавливаем максимально возможное ограничение как для hard- так и для soft-параметра. Дальше нужно закрыть этот файл и обновить конфигурацию сервисов:
Затем перезагрузить нужный сервис:
Убедится, что для вашего сервиса применились нужные ограничения, можно, открыв файл по пути /proc/pid_сервиса/limits. Сначала смотрим PID нужного нам сервиса:
Затем смотрим информацию:
Увеличить Max Open File Limit в Unix/Linux
Приведу команды на различные Unix/Linux ОС
Увеличить Max Open File Limit в Linux
Для начала проверим какой предел установлен в ОС:
# cat /proc/sys/fs/file-max
Увеличиваем данный предел в Linux
Мы можем увеличить лимиты для открытых файлов:
- Временно.
- Постоянно.
-===ВРЕМЕННО===-
Если есть необходимость увеличить лимит временно (для тестирования, например), то можно это сделать так:
# sysctl -w fs.file-max=500000
Или:
# echo "500000" > /proc/sys/fs/file-max
Вот еще один пример:
# ulimit -n 65635
-===ПОСТОЯННО===-
Если есть необходимость увеличить лимит навсегда, то можно это сделать так:
# vim /etc/sysctl.conf fs.file-max = 500000
Эти настройки будут сохраняться даже после перезагрузки системы. После добавления конфигурации в файл, выполните следующую команду, чтобы изменения вступили в силу:
# sysctl -p
Настройка лимитов для каждого пользователя
# vim /etc/security/limits.conf
Добавляем параметры:
* hard nofile 500000 * soft nofile 500000 root hard nofile 500000 root soft nofile 500000
Проверка установленных лимитов
Используйте следующую команду, чтобы увидеть максимальное чисто для открытых файлов:
# cat /proc/sys/fs/file-max
Подключаемся от пользователя (у меня это nginx):
# su nginx
Проверяем параметры Hard лимитов:
# ulimit -Hn
В консоле, можно ввести данную команду (очень удобно отображает):
# for pid in `pidof nginx`; do echo "$(< /proc/$pid/cmdline)"; egrep 'files|Limit' /proc/$pid/limits; echo "Currently open files: $(ls -1 /proc/$pid/fd | wc -l)"; echo; done
Проверяем параметры лимитов Soft:
# ulimit -Sn
Увеличить Max Open File Limit в Mac OS X
Выполним проверку лимитов с помощью:
$ launchctl limit maxfiles
Где:
- Первый аргумент — soft limit.
- Второй аргумент — hard limit.
Можно прописать в файл:
# vim ~/.bash_profile
Следующее значение:
ulimit -n 65536 200000
Вот и все!
Увеличюем nginx worker_rlimit_nofile в nginx ( на уровне Nginx)
В nginx также можно увеличить лимиты с директивой worker_rlimit_nofile, которая позволяет увеличить этот лимит, если это не хватает данного ресурса на лету на уровне процесса:
# vim /etc/nginx/nginx.conf
И прописываем (редактируем):
# set open fd limit to 30000 worker_rlimit_nofile 30000;
После чего, проверяем конфигурацию nginx и перезапускаем его:
Save and close the file. Reload nginx web server, enter:
# nginx -t && service nginx -s reload
ulimit в Kali Linux
Включение ограничений на основе PAM в Unix/Lixux
Для Debian/Ubuntu
Редактируем файл (Debian/Ubuntu):
# vim /etc/pam.d/common-session
Вставляем:
session required pam_limits.so
Открываем еще один файл:
# vim /etc/security/limits.conf
Прописываем лимиты:
* soft nofile 65536 * hard nofile 200000
Открываем:
# vim /etc/ssh/sshd_config
И, приводим к виду:
UseLogin yes
И выполняем рестарт:
# reboot
Для CentOS/RedHat/Fedora
Редактируем файл (Debian/Ubuntu):
# vim /etc/pam.d/login
Вставляем:
session required pam_limits.so
Открываем еще один файл:
# vim /etc/security/limits.conf
Прописываем лимиты:
* soft nofile 65536 * hard nofile 200000
Открываем:
# vim /etc/ssh/sshd_config
И, приводим к виду:
UseLogin yes
И выполняем рестарт:
# reboot
У меня все! Статья «Увеличить Max Open File Limit в Unix/Linux», завершено.