dev-sec.ssh-hardening
ssh强化(Ansible角色)
注意: 该角色已迁移到我们的硬化集合:
请在那边提出任何问题和拉取请求!
需求
- Ansible > 2.5
角色变量
network_ipv6_enable
- 默认:false
- 描述:如果需要IPv6则为true。
ssh_listen_to
也必须设置为监听IPv6地址(例如[::]
)。
ssh_server_ports
- 默认:['22']
- 描述:ssh服务器应监听的端口
ssh_client_port
- 默认:'22'
- 描述:ssh客户端应连接的端口
ssh_listen_to
- 默认:['0.0.0.0']
- 描述:ssh服务器应监听的一个或多个IP地址。默认是所有IPv4地址,但出于安全原因应配置为特定地址!
ssh_host_key_files
- 默认:[]
- 描述:sshd的主机密钥。如果为空,将使用
['/etc/ssh/ssh_host_rsa_key', '/etc/ssh/ssh_host_ecdsa_key', '/etc/ssh/ssh_host_ed25519_key']
,具体取决于安装的sshd版本的支持情况。
ssh_host_key_algorithms
- 默认:[]
- 描述:服务器提供的主机密钥算法。如果为空,将使用默认列表,否则将使用指定的算法列表覆盖该设置。
ssh_client_alive_interval
- 默认:600
- 描述:指定发送保活消息的间隔
ssh_client_alive_count
- 默认:3
- 描述:定义发送保活消息的频率
ssh_permit_tunnel
- 默认:false
- 描述:如果需要SSH端口隧道,则为true
ssh_remote_hosts
- 默认:[]
- 描述:一个或多个主机及其ssh客户端的自定义选项。默认为空。请参见
defaults/main.yml
中的示例。
ssh_permit_root_login
- 默认:否
- 描述:禁用根登录。设置为
without-password
或yes
以启用根登录
ssh_allow_tcp_forwarding
- 默认:否
- 描述:
'no'
禁用TCP转发。设置为'yes'
以允许TCP转发。如果您使用的OpenSSH版本>=6.2,可以指定'yes'
,'no'
,'all'
或'local'
。
注意:传递给该变量的值必须是字符串,因此值'yes'
和'no'
应统一用引号。
ssh_gateway_ports
- 默认:
false
- 描述:
false
禁用将转发端口绑定到非回环地址。设置为true
以强制在通配符地址上绑定。设置为clientspecified
以允许客户端指定要绑定的地址。
- 默认:
ssh_allow_agent_forwarding
- 默认:false
- 描述:false禁用代理转发。设置为true以允许代理转发。
ssh_x11_forwarding
- 默认:false
- 描述:false禁用X11转发。设置为true以允许X11转发。
ssh_pam_support
- 默认:true
- 描述:如果SSH支持PAM则为true。
ssh_use_pam
- 默认:true
- 描述:false禁用pam认证。
ssh_gssapi_support
- 默认:false
- 描述:如果SSH支持GSSAPI则为true。
ssh_kerberos_support
- 默认:true
- 描述:如果SSH支持Kerberos则为true。
ssh_deny_users
- 默认:''
- 描述:如果指定,则禁止与某个模式匹配的用户登录。
ssh_allow_users
- 默认:''
- 描述:如果指定,则仅允许与某个模式匹配的用户登录。
ssh_deny_groups
- 默认:''
- 描述:如果指定,则禁止主组或附加组列表与某个模式匹配的用户登录。
ssh_allow_groups
- 默认:''
- 描述:如果指定,则仅允许主组或附加组列表与某个模式匹配的用户登录。
ssh_authorized_keys_file
- 默认:''
- 描述:更改包含可以用于用户身份验证的公钥的默认文件。
ssh_trusted_user_ca_keys_file
- 默认:''
- 描述:指定包含受信任的证书授权公钥的文件,用于签署用户证书。
ssh_trusted_user_ca_keys
- 默认:[]
- 描述:设置用于签署用户证书的受信任的证书授权公钥。仅在设置
ssh_trusted_user_ca_keys_file
时使用。
ssh_authorized_principals_file
- 默认:''
- 描述:指定包含被允许的主体的文件。仅在设置
ssh_trusted_user_ca_keys_file
时使用。
ssh_authorized_principals
- 默认:[]
- 描述:包含文件路径和授权主体的哈希列表,所有选项请参见
default_custom.yml
。仅在设置ssh_authorized_principals_file
时使用。
ssh_print_motd
- 默认:false
- 描述:false禁用打印每日信息(MOTD)
ssh_print_pam_motd
- 默认:false
- 描述:false禁用通过pam打印每日信息(MOTD)(适用于Debian和Ubuntu)
ssh_print_last_log
- 默认:false
- 描述:false禁用显示上次登录信息
sftp_enabled
- 默认:false
- 描述:true启用sftp配置
sftp_umask
- 默认:'0027'
- 描述:指定sftp的umask
sftp_chroot
- 默认:true
- 描述:false禁用sftp的chroot
sftp_chroot_dir
- 默认:/home/%u
- 描述:更改默认的sftp chroot位置
ssh_client_roaming
- 默认:false
- 描述:启用实验性客户端漫游
sshd_moduli_file
- 默认:'/etc/ssh/moduli'
- 描述:SSH moduli 文件的路径
sshd_moduli_minimum
- 默认:2048
- 描述:移除小于定义大小的Diffie-Hellman参数,以减轻日志攻击。
ssh_challengeresponseauthentication
- 默认:false
- 描述:指定是否允许挑战-响应认证(例如通过PAM)。
ssh_client_password_login
- 默认:false
- 描述:
true
允许使用ssh客户端的基于密码的认证。
ssh_server_password_login
- 默认:false
- 描述:
true
允许使用ssh服务器的基于密码的认证。
ssh_banner
- 默认:
false
- 描述:
true
在登录时打印横幅。
- 默认:
ssh_banner_path
- 默认:'/etc/sshd/banner.txt'
- 描述:SSH横幅文件的路径
ssh_client_hardening
- 默认:
true
- 描述:
false
停止加固客户端
- 默认:
ssh_client_port
- 默认:'22'
- 描述:指定连接到远程主机的端口号。
ssh_client_compression
- 默认:
false
- 描述:指定客户端是否请求压缩。
- 默认:
ssh_compression
- 默认:
false
- 描述:指定用户成功认证后是否启用服务器侧压缩。
- 默认:
ssh_login_grace_time
- 默认:
30s
- 描述:指定成功认证到SSH服务器的时间。
- 默认:
ssh_max_auth_retries
- 默认:
2
- 描述:指定每个连接允许的最大认证尝试次数。
- 默认:
ssh_max_sessions
- 默认:
10
- 描述:指定来源连接允许的最大开放会话数。
- 默认:
ssh_print_debian_banner
- 默认:
false
- 描述:
true
打印特定于Debian的横幅。
- 默认:
ssh_server_enabled
- 默认:
true
- 描述:
false
禁用opensshd服务器。
- 默认:
ssh_server_hardening
- 默认:
true
- 描述:
false
停止加固服务器。
- 默认:
ssh_server_match_address
- 默认:''
- 描述:引入条件块。如果Match行上的所有条件都满足,后续行中的关键字将覆盖配置文件全局部分中设置的内容,直到另一个Match行或文件结束。
ssh_server_match_group
- 默认:''
- 描述:引入条件块。如果Match行上的所有条件都满足,后续行中的关键字将覆盖配置文件全局部分中设置的内容,直到另一个Match行或文件结束。
ssh_server_match_user
- 默认:''
- 描述:引入条件块。如果Match行上的所有条件都满足,后续行中的关键字将覆盖配置文件全局部分中设置的内容,直到另一个Match行或文件结束。
ssh_server_match_local_port
- 默认:''
- 描述:引入条件块。如果Match行上的所有条件都满足,后续行中的关键字将覆盖配置文件全局部分中设置的内容,直到另一个Match行或文件结束。
ssh_server_permit_environment_vars
- 默认:
no
- 描述:
yes
以指定处理用户的/.ssh/environment和/.ssh/authorized_keys中的环境变量选项。通过openssh版本7.8,可以指定环境变量名称的白名单,除了全局yes
或no
设置。
- 默认:
ssh_server_accept_env_vars
- 默认:''
- 描述:指定客户端发送的将被复制到会话环境中的环境变量,多个环境变量可以用空格分隔。
ssh_use_dns
- 默认:
false
- 描述:指定sshd是否应查找远程主机名,并检查解析后的远程IP地址的主机名是否映射回同一IP地址。
- 默认:
ssh_server_revoked_keys
- 默认:[]
- 描述:被ssh服务器始终拒绝的已撤销公钥列表, útil para撤销已知的弱或被攻击的密钥。
ssh_max_startups
- 默认:'10:30:100'
- 描述:指定对SSH守护程序的最大并发未认证连接数。
ssh_macs
- 默认:[]
- 描述:更改此列表以覆盖macs。默认值请参见
defaults/main.yml
。
ssh_kex
- 默认:[]
- 描述:更改此列表以覆盖kexs。默认值请参见
defaults/main.yml
。
ssh_ciphers
- 默认:[]
- 描述:更改此列表以覆盖密钥。默认值请参见
defaults/main.yml
。
ssh_custom_options
- 默认:[]
- 描述:SSH客户端配置的自定义行。
sshd_custom_options
- 默认:[]
- 描述:SSH守护程序配置的自定义行。
sshd_syslog_facility
- 默认:'AUTH'
- 描述:在记录sshd消息时使用的设施代码。
sshd_log_level
- 默认:'VERBOSE'
- 描述:在记录sshd消息时使用的详细级别。
sshd_strict_modes
- 默认:true
- 描述:在接受登录之前检查用户文件和主目录的文件模式和所有权。
sshd_authenticationmethods
- 默认:
publickey
- 描述:指定用户必须成功完成的认证方法以获得访问权限。确保为所选认证方法设置所有必需的变量。默认值请参见
defaults/main.yml
。
- 默认:
配置未在角色变量中列出的设置
如果您想配置未在上述列表中的ssh选项,可以使用ssh_custom_options
(用于/etc/ssh/ssh_config
)或sshd_custom_options
(用于/etc/ssh/sshd_config
)来设置它们。 这些选项将在文件开头设置,因此您可以覆盖文件中后面的选项。
示例剧本:
- hosts: localhost
roles:
- dev-sec.ssh-hardening
vars:
ssh_custom_options:
- "Include /etc/ssh/ssh_config.d/*"
sshd_custom_options:
- "AcceptEnv LANG"
更改默认端口和幂等性
该角色使用默认端口22或在清单中配置的端口连接到服务器。如果通过ssh_server_ports
更改默认ssh
端口,一旦重启ssh服务器,它仍然会尝试使用先前的端口进行连接。为了在同一服务器上再次运行该角色,必须更新清单以使用新的ssh端口。
如果幂等性很重要,请考虑使用角色ssh-hardening-fallback
,这是一个围绕该角色的包装器,如果配置的端口不可达,则会回退到端口22。
示例剧本
- hosts: localhost
roles:
- dev-sec.ssh-hardening
本地测试
本地测试角色的首选方法是使用Docker。您需要在系统上安装Docker。有关适合您系统的Docker软件包,请参见入门指南。
您也可以使用vagrant和Virtualbox或VMWare在本地运行测试。您需要在系统上安装Virtualbox和Vagrant。有关适合您系统的vagrant软件包,请参见Vagrant下载。我们所有的测试都使用test-kitchen
。如果您不熟悉test-kitchen
,请查看他们的指南。
接下来安装test-kitchen:
# 安装依赖
gem install bundler
bundle install
使用Docker测试
# 在一台机器上快速测试
bundle exec kitchen test ssh-ubuntu1804-ansible-latest
# 在所有机器上测试
bundle exec kitchen test
# 开发时
bundle exec kitchen create ssh-ubuntu1804-ansible-latest
bundle exec kitchen converge ssh-ubuntu1804-ansible-latest
bundle exec kitchen verify ssh-ubuntu1804-ansible-latest
# 清理
bundle exec kitchen destroy ssh-ubuntu1804-ansible-latest
使用Virtualbox测试
# 在一台机器上快速测试
KITCHEN_YAML=".kitchen.vagrant.yml" bundle exec kitchen test ssh-ubuntu-1804
# 在所有机器上测试
KITCHEN_YAML=".kitchen.vagrant.yml" bundle exec kitchen test
# 开发时
KITCHEN_YAML=".kitchen.vagrant.yml" bundle exec kitchen create ssh-ubuntu-1804
KITCHEN_YAML=".kitchen.vagrant.yml" bundle exec kitchen converge ssh-ubuntu-1804
有关更多信息,请参见test-kitchen。
常见问题 / 陷阱
我无法登录到我的帐户。我已注册客户端密钥,但仍然无法登录。
如果您已经排除了所有典型的问题(防火墙、网络、密钥丢失、密钥错误、账户禁用等),那么可能是您的帐户被锁定。最快的方式是查看您用户的密码哈希:
sudo grep myuser /etc/shadow
如果哈希中包含!
,则您的帐户已被锁定:
myuser:!:16280:7:60:7:::
解决此问题的正确方法是解锁账户(passwd -u myuser
)。如果用户没有密码,您可以通过以下方式解锁:
usermod -p "*" myuser
另外,如果您打算使用PAM,您可以通过ssh_use_pam: true
进行启用。PAM允许锁定的用户通过密钥登录。
为什么我的应用程序通过SSH不再连接?
总是先查看日志文件,如果可能的话,查看连接时客户端和服务器之间的协商。
我们发现一些基于python和ruby的应用程序存在由于使用过时的加密套件而导致的问题。这与该加固模块发生冲突,该模块将加密、消息认证码(MAC)和密钥交换(KEX)算法的列表减少到了更安全的选择。
使用此角色后,Ansible的模板/复制/文件模块不再工作!
该角色默认禁用SFTP。Ansible默认使用SFTP将文件传输到远程主机。您需要在您的ansible.cfg中设置scp_if_ssh = True
。这样Ansible使用SCP来复制文件。或者,您可以通过将sftp_enabled
设置为true
来再次启用SFTP。
由于权限不足无法重启sshd服务
如果您在运行处理程序“restart sshd”时遇到以下错误:
无法重启ssh服务:无法重启ssh.service:访问被拒绝
或
无法连接到总线:没有这样的文件或目录
请以root
身份运行剧本(在剧本级别时无become: yes
),或将become: yes
添加到处理程序。
贡献
请参见贡献指南。
许可证和作者
- 作者:: Sebastian Gumprich
- 作者:: Christoph Hartmann chris@lollyrock.com
根据Apache许可证第2.0版(“许可证”)许可; 您不得在不遵循许可证的情况下使用此文件。 您可以在以下网站获取许可证副本:
http://www.apache.org/licenses/LICENSE-2.0
除非适用的法律或书面协议另有规定,否则根据许可证分发的软件按“原样”提供,没有任何形式的保证或条件,无论是明示还是暗示。请参见许可证以了解有关权限和限制的具体规定。
This Ansible role provides numerous security-related ssh configurations, providing all-round base protection.
ansible-galaxy install dev-sec.ssh-hardening