如何在启动时为服务设置ulimits?

我需要mysql来使用大页面来设置ulimit – 我在limits.conf中做了这个。 但是,limits.conf(pam_limits.so)不能读入init,只能读取“真实”的shell。 我之前通过在initscript start函数中添加一个“ulimit -l”来解决这个问题。 我需要某种可重复的方式来做到这一点,现在这些盒子是由厨师pipe理的,我们不想接pipe一个由RPM实际拥有的文件。

$ echo "* hard nofile 102400" >> /etc/security/limits.conf $ echo "* soft nofile 102400" >> /etc/security/limits.conf $ sysctl -w fs.file-max=102400 $ sysctl -p 

这4个步骤可以立即改变您的系统的限制,并且可以在您重新启动后继续工作。 您可以根据需要将数字“102400”更改为Linux系统中的最大打开文件数。 和

 $ sysctl -p 

如果没有指定,则从指定的文件或/etc/sysctl.conf中加载sysctl设置。

/etc/sysctl.conf应该能够设置ulimits项目。 我没能够很好地testing这个,但是调查显示你应该能够在sysctl.conf中设置后停下来。

我发现各种主题显示它仍然是一个问题,虽然我的团队和我已经讨论了一些select,我们已经find了两个潜在的解决方法。

选项1:大多数rhel initscripts源码/etc/init.d/functions,您可以在那里更改ulimit设置

选项2:init宣称/ etc / initscript每次在init产生任何内容之前都会获取: http : //linux.die.net/man/5/initscript 。 有意思的是,他们说人们可以设置ulimit =)

基于此url的自包含配方片段:

 http://pro.benjaminste.in/post/318453669/increase-the-number-of-file-descriptors-on-centos- 

食谱片段:

 ruby_block "edit /etc/sysctl.conf" do _file = "/etc/sysctl.conf" _comment = "# TWEAK BY CHEF" _content = "fs.file-max = 512000" block do file = Chef::Util::FileEdit.new(_file) file.insert_line_if_no_match(/#{Regexp.escape(_comment)}/, "#{_comment}\n#{_content}") file.write_file end not_if "cat #{_file} | grep '#{_comment}'" notifies :run, "execute[sysctl -p]", :immediately end execute "sysctl -p" do command "sysctl -p" returns 255 # which would normally signify error, but doesn't on sysctl on CentOS action :nothing end ruby_block "edit /etc/security/limits.conf" do _file = "/etc/security/limits.conf" _comment = "# TWEAK BY CHEF" _content = "* - nofile 65535" block do file = Chef::Util::FileEdit.new(_file) file.insert_line_if_no_match(/#{Regexp.escape(_comment)}/, "#{_comment}\n#{_content}") file.write_file end not_if "cat #{_file} | grep '#{_comment}'" end 

我的解决scheme只是在我们的厨师食谱做这个:

 # Ensure ulimits are properly set for the initscript bash "Set Ulimits" do user "root" code <<-EOH echo -e "n#Setting ulimits. Performed by chef recipe MYSQLULIMIT\nulimit -l" >> /etc/sysconfig/init EOH not_if "grep MYSQLULIMIT /etc/sysconfig/init" end 

这会导致ulimit -l被设置为所有的initscripts,这在某些环境中可能是不受欢迎的,但是对我来说很好。

在一个完美的世界中,我会更新RPM以包含/etc/sysconfig/mysqld ,并将相同的ulimit -l命令放在那里。

不知道这是如何发行特定的,但我已经通过在Ubuntu中使用/etc/security/limits.d/20-somefile.conf来增加安全限制。

我没有修改现有的文件,而是在我的食谱中有一个ERB模板,在属性文件中设置默认属性,然后不必担心使用带有“insert_line_if_no_match”东西的ruby块 – 这似乎有点复杂,配方更像这样可读:

 execute "activate_sysctl" do user "root" command "sysctl -p /etc/sysctl.d/10-filemax.conf" action :nothing end template "/etc/sysctl.d/10-filemax.conf" do source "system/filemax.conf" action :create notifies :run, "execute[activate_sysctl]", :immediately end 

然后这是我的模板文件:

 fs.filemax = <%= node[:mycookbook][:system_fs_filemax] %> 

根据手册页ulimit被弃用。 你需要使用setrlimit。 问题是这是一个系统调用,而不是一个bash命令。

我和主pipe有这个问题,这就是我发现的。 如果进程没有configuration文件,允许您调用setrlimit()系统调用。 在/etc/init.d bash脚本中使用ulimit进行设置。 这是启动你的过程的服务脚本。

如果进程有一个configuration文件,像supervisor d那么你可以使用该configuration文件来设置文件的数量,并让进程直接调用setrlimits()。

主pipe: http : //supervisord.org/configuration.html#supervisord-section-settings

TomcaT: http : //www.jayway.com/2012/02/11/how-to-really-fix-the-too-many-open-files-problem-for-tomcat-in-ubuntu/

尝试在/etc/sysctl.conf文件中设置

我其实写了一个私人厨师食谱,用来为我们设置ulimit,它工作得很好。 对于Ubuntu,我们发现如果你想要一个全局的ulimit设置,就需要下面的技巧:

将以下内容添加到您的共同会话中:

 session required pam_limits.so 

并在limit.conf中必须具有以下内容:

 * soft nofile 64000 * hard nofile 65000 root soft nofile 64000 root hard nofile 65000 

根部分很重要,因为看起来没有一些初始化脚本不能正常工作。 所以我们有一个厨师食谱,设置以下,它的作品很好。

我们用于Tomcat的另一个选项是部署Tomcat,然后使用自定义设置ulimit并重新启动tomcat来覆盖init脚本。 这个工程很好,但是比第一个更有趣。

我希望这可以帮助,也许有一天我可以开放我们内部的食谱,因为它很简单,但可能对你这样的人有帮助。