REORG: startup: move nofile limit checks in limits.c

Let's encapsulate the code, which checks the applied nofile limit into
a separate helper check_nofile_lim_and_prealloc_fd(). Let's keep in this new
function scope the block, which tries to create a copy of FD with the highest
number, if prealloc-fd is set in the configuration.
This commit is contained in:
Valentine Krasnobaeva 2024-11-25 16:15:17 +01:00 committed by William Lallemand
parent 14f5e00d38
commit fbc534a6fa
3 changed files with 42 additions and 29 deletions

View File

@ -7,6 +7,8 @@
#ifndef _HAPROXY_LIMITS_H
#define _HAPROXY_LIMITS_H
#include <errno.h>
#include <fcntl.h>
#include <sys/resource.h>
#include <haproxy/compat.h>
@ -40,6 +42,7 @@ int raise_rlim_nofile(struct rlimit *old_limit, struct rlimit *new_limit);
void set_global_maxconn(void);
void apply_nofile_limit(void);
void apply_memory_limit(void);
void check_nofile_lim_and_prealloc_fd(void);
#endif /* _HAPROXY_LIMITS_H */

View File

@ -23,8 +23,6 @@
#include <netinet/in.h>
#include <arpa/inet.h>
#include <netdb.h>
#include <fcntl.h>
#include <errno.h>
#include <signal.h>
#include <stdarg.h>
#include <sys/resource.h>
@ -2345,8 +2343,6 @@ static void step_init_3(void)
*/
static void step_init_4(void)
{
struct rlimit limit;
/* MODE_QUIET is applied here, it can inhibit alerts and warnings below this line */
if (getenv("HAPROXY_MWORKER_REEXEC") != NULL) {
/* either stdin/out/err are already closed or should stay as they are. */
@ -2366,31 +2362,10 @@ static void step_init_4(void)
* be able to restart the old pids.
*/
/* check ulimits */
limit.rlim_cur = limit.rlim_max = 0;
getrlimit(RLIMIT_NOFILE, &limit);
if (limit.rlim_cur < global.maxsock) {
if (global.tune.options & GTUNE_STRICT_LIMITS) {
ha_alert("[%s.main()] FD limit (%d) too low for maxconn=%d/maxsock=%d. "
"Please raise 'ulimit-n' to %d or more to avoid any trouble.\n",
progname, (int)limit.rlim_cur, global.maxconn, global.maxsock,
global.maxsock);
exit(1);
}
else
ha_alert("[%s.main()] FD limit (%d) too low for maxconn=%d/maxsock=%d. "
"Please raise 'ulimit-n' to %d or more to avoid any trouble.\n",
progname, (int)limit.rlim_cur, global.maxconn, global.maxsock,
global.maxsock);
}
if (global.prealloc_fd && fcntl((int)limit.rlim_cur - 1, F_GETFD) == -1) {
if (dup2(0, (int)limit.rlim_cur - 1) == -1)
ha_warning("[%s.main()] Unable to preallocate file descriptor %d : %s",
progname, (int)limit.rlim_cur - 1, strerror(errno));
else
close((int)limit.rlim_cur - 1);
}
/* check current nofile limit reported via getrlimit() and check if we
* can preallocate FDs, if global.prealloc_fd is set.
*/
check_nofile_lim_and_prealloc_fd();
/* update the ready date a last time to also account for final setup time */
clock_update_date(0, 1);

View File

@ -500,3 +500,38 @@ void apply_memory_limit(void)
}
}
/* Checks the current nofile limit via getrlimit and preallocates the
* (limit.rlim_cur - 1) of FDs. It may terminate the process, if its current
* nofile limit is lower than global.maxsock and there is no 'no strict-limits'
* in the global section.
*/
void check_nofile_lim_and_prealloc_fd(void)
{
struct rlimit limit;
limit.rlim_cur = limit.rlim_max = 0;
getrlimit(RLIMIT_NOFILE, &limit);
if (limit.rlim_cur < global.maxsock) {
if (global.tune.options & GTUNE_STRICT_LIMITS) {
ha_alert("[%s.main()] FD limit (%d) too low for maxconn=%d/maxsock=%d. "
"Please raise 'ulimit-n' to %d or more to avoid any trouble.\n",
progname, (int)limit.rlim_cur, global.maxconn, global.maxsock,
global.maxsock);
exit(1);
}
else
ha_alert("[%s.main()] FD limit (%d) too low for maxconn=%d/maxsock=%d. "
"Please raise 'ulimit-n' to %d or more to avoid any trouble.\n",
progname, (int)limit.rlim_cur, global.maxconn, global.maxsock,
global.maxsock);
}
if (global.prealloc_fd && fcntl((int)limit.rlim_cur - 1, F_GETFD) == -1) {
if (dup2(0, (int)limit.rlim_cur - 1) == -1)
ha_warning("[%s.main()] Unable to preallocate file descriptor %d : %s",
progname, (int)limit.rlim_cur - 1, strerror(errno));
else
close((int)limit.rlim_cur - 1);
}
}