Skip to content

Commit bb65791

Browse files
authored
Add j2 template for enable pam_limit and limit SSH session (#10298)
#### Why I did it When too many user login concurrently and run commands, SONiC may kernel panic on some device which has very limited memory. #### How I did it Add j2 template for setup pam_limit plugin for limit SSH session per-user. #### How to verify it Manually validate the j2 template can generate correct config file. #### Which release branch to backport (provide reason below if selected) - [x] 201811 - [ ] 201911 - [ ] 202006 - [x] 202012 - [x] 202106 - [x] 202111 #### Description for the changelog Add j2 template for setup pam_limit plugin for limit SSH session per-user. #### A picture of a cute animal (not mandatory but encouraged)
1 parent beea989 commit bb65791

File tree

3 files changed

+146
-0
lines changed

3 files changed

+146
-0
lines changed

files/image_config/hostcfgd/hostcfgd

+65
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,10 @@ PAM_AUTH_CONF_TEMPLATE = "/usr/share/sonic/templates/common-auth-sonic.j2"
1717
NSS_TACPLUS_CONF = "/etc/tacplus_nss.conf"
1818
NSS_TACPLUS_CONF_TEMPLATE = "/usr/share/sonic/templates/tacplus_nss.conf.j2"
1919
NSS_CONF = "/etc/nsswitch.conf"
20+
PAM_LIMITS_CONF_TEMPLATE = "/usr/share/sonic/templates/pam_limits.j2"
21+
LIMITS_CONF_TEMPLATE = "/usr/share/sonic/templates/limits.conf.j2"
22+
PAM_LIMITS_CONF = "/etc/pam.d/pam-limits-conf"
23+
LIMITS_CONF = "/etc/security/limits.conf"
2024

2125
# TACACS+
2226
TACPLUS_SERVER_PASSKEY_DEFAULT = ""
@@ -232,6 +236,63 @@ class AaaCfg(object):
232236
syslog.syslog(syslog.LOG_INFO, 'pam.d files updated auth={} global={}'.
233237
format(auth, tacplus_global))
234238

239+
class PamLimitsCfg(object):
240+
"""
241+
PamLimit Config Daemon
242+
1) The pam_limits PAM module sets limits on the system resources that can be obtained in a user-session.
243+
2) Purpose of this daemon is to render pam_limits config file.
244+
"""
245+
def __init__(self, config_db):
246+
self.config_db = config_db
247+
self.hwsku = ""
248+
self.type = ""
249+
250+
# Load config from ConfigDb and render config file/
251+
def update_config_file(self):
252+
device_metadata = self.config_db.get_table('DEVICE_METADATA')
253+
if "localhost" not in device_metadata:
254+
return
255+
256+
self.read_localhost_config(device_metadata["localhost"])
257+
self.render_conf_file()
258+
259+
# Read localhost config
260+
def read_localhost_config(self, localhost):
261+
if "hwsku" in localhost:
262+
self.hwsku = localhost["hwsku"]
263+
else:
264+
self.hwsku = ""
265+
266+
if "type" in localhost:
267+
self.type = localhost["type"]
268+
else:
269+
self.type = ""
270+
271+
# Render pam_limits config files
272+
def render_conf_file(self):
273+
env = jinja2.Environment(loader=jinja2.FileSystemLoader('/'), trim_blocks=True)
274+
env.filters['sub'] = sub
275+
276+
try:
277+
template_file = os.path.abspath(PAM_LIMITS_CONF_TEMPLATE)
278+
template = env.get_template(template_file)
279+
pam_limits_conf = template.render(
280+
hwsku=self.hwsku,
281+
type=self.type)
282+
with open(PAM_LIMITS_CONF, 'w') as f:
283+
f.write(pam_limits_conf)
284+
285+
template_file = os.path.abspath(LIMITS_CONF_TEMPLATE)
286+
template = env.get_template(template_file)
287+
limits_conf = template.render(
288+
hwsku=self.hwsku,
289+
type=self.type)
290+
with open(LIMITS_CONF, 'w') as f:
291+
f.write(limits_conf)
292+
except Exception as e:
293+
syslog.syslog(syslog.LOG_ERR,
294+
"modify pam_limits config file failed with exception: {}"
295+
.format(e))
235296

236297
class HostConfigDaemon:
237298
def __init__(self):
@@ -242,6 +303,10 @@ class HostConfigDaemon:
242303
self.aaacfg = AaaCfg(self.config_db)
243304
self.iptables = Iptables()
244305

306+
# Initialize PamLimitsCfg
307+
self.pamLimitsCfg = PamLimitsCfg(self.config_db)
308+
self.pamLimitsCfg.update_config_file()
309+
245310

246311
def timer_load(self):
247312
global global_lock
+69
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,69 @@
1+
# /etc/security/limits.conf
2+
#
3+
# This file generate by j2 template file: src/sonic-host-services-data/templates/limits.conf.j2
4+
#
5+
# Each line describes a limit for a user in the form:
6+
#
7+
# <domain> <type> <item> <value>
8+
#
9+
# Where:
10+
# <domain> can be:
11+
# - a user name
12+
# - a group name, with @group syntax
13+
# - the wildcard *, for default entry
14+
# - the wildcard %, can be also used with %group syntax,
15+
# for maxlogin limit
16+
# - NOTE: group and wildcard limits are not applied to root.
17+
# To apply a limit to the root user, <domain> must be
18+
# the literal username root.
19+
#
20+
# <type> can have the two values:
21+
# - "soft" for enforcing the soft limits
22+
# - "hard" for enforcing hard limits
23+
#
24+
# <item> can be one of the following:
25+
# - core - limits the core file size (KB)
26+
# - data - max data size (KB)
27+
# - fsize - maximum filesize (KB)
28+
# - memlock - max locked-in-memory address space (KB)
29+
# - nofile - max number of open file descriptors
30+
# - rss - max resident set size (KB)
31+
# - stack - max stack size (KB)
32+
# - cpu - max CPU time (MIN)
33+
# - nproc - max number of processes
34+
# - as - address space limit (KB)
35+
# - maxlogins - max number of logins for this user
36+
# - maxsyslogins - max number of logins on the system
37+
# - priority - the priority to run user process with
38+
# - locks - max number of file locks the user can hold
39+
# - sigpending - max number of pending signals
40+
# - msgqueue - max memory used by POSIX message queues (bytes)
41+
# - nice - max nice priority allowed to raise to values: [-20, 19]
42+
# - rtprio - max realtime priority
43+
# - chroot - change root to directory (Debian-specific)
44+
#
45+
#
46+
# <value> is related with <item>:
47+
# All items support the values -1, unlimited or infinity indicating
48+
# no limit, except for priority and nice.
49+
#
50+
# If a hard limit or soft limit of a resource is set to a valid value,
51+
# but outside of the supported range of the local system, the system
52+
# may reject the new limit or unexpected behavior may occur. If the
53+
# control value required is used, the module will reject the login if
54+
# a limit could not be set.
55+
#
56+
# <domain> <type> <item> <value>
57+
#
58+
59+
# * soft core 0
60+
# root hard core 100000
61+
# * hard rss 10000
62+
# @student hard nproc 20
63+
# @faculty soft nproc 20
64+
# @faculty hard nproc 50
65+
# ftp hard nproc 0
66+
# ftp - chroot /ftp
67+
# @student - maxlogins 4
68+
69+
# End of file
+12
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
#THIS IS AN AUTO-GENERATED FILE
2+
#
3+
# This file generate by j2 template file: src/sonic-host-services-data/templates/pam_limits.j2
4+
#
5+
# /etc/pam.d/pam-limits settings common to all services
6+
# This file is included from other service-specific PAM config files,
7+
# and should contain a list of the authentication modules that define
8+
# the central authentication scheme for use on the system
9+
# (e.g., /etc/shadow, LDAP, Kerberos, etc.). The default is to use the
10+
# traditional Unix authentication mechanisms.
11+
#
12+
# here are the per-package modules (the "Primary" block)

0 commit comments

Comments
 (0)