1、背景

安全整改过程中针对服务器共性问题的修复,SSH弱密钥交换算法漏洞为例,以上篇中的《Centos7修复ssh弱密钥交换算法漏洞》为场景结合优化处理。ansible环境搭建可以参考《win10系统下ansible环境的搭建》

2、目的

批量修复服务器的SSH弱密钥交换算法漏洞

3、环境说明

名称

型号

备注

window10

教育版64位

主操作系统

WSL

1.0

介质

Linux

ubuntu18.04LTS

子操作系统

ansible

2.9.10

运维工具

Centos7

7.9.2009

远程主机操作系统

4、工具选型

本次以ansible工具为例进行操作。

5、问题说明

安全扫描厂家提供如下信息

漏洞名称

漏洞描述

等级

安全建议

SSH Weak Key Exchange Algorithms Enabled SSH 弱密钥交换算法已启用

远程 SSH 服务器配置为允许被认为是弱的密钥交换算法。这是基于 IETF 草案文档 Key Exchange (KEX) Method Updates and Recommendations for Secure Shell (SSH) draft-ietf-curdle-ssh-kex-sha2-20。第 4 节列出了关于不应和不得启用的密钥交换算法的指南。这包括:diffie-hellman-group-exchange-sha1、diffie-hellman-group1-sha1、gss-gex-sha1-、gss-group1-sha1-、gss-group14-sha1-*、rsa1024-sha1

低危

联系供应商或查阅产品文档以禁用弱算法。

6、处理说明

6.1、方案选型

两种处理方案:

方案一 通过调整配置文件,规避此安全漏洞,
方案二 升级ssh程序,修复此安全漏洞

本文选取方案二

项目名称

原版本号

升级后版本号

OpenSSL

1.0.2k-fips

3.0.0

OpenSSH

7.4p1

8.8p1

6.2、处理思路

6.2.1、漏洞原因:

该漏洞是由于操作系统自带软件版本过旧,导致的漏洞,Centos7.x及以前版本会存在此漏洞。

6.2.2、风险点分析

远程登陆使用的是ssh服务进行,修复过程中会产生服务启停操作,即时会有远程登陆无法登陆的情况,故在处理过程中需要考虑到此风险,

6.2.3、风险应对

针对此风险应对措施如下:

1、服务器开启telnet服务,保证ssh启停过程中可以通过telnet登陆服务器操作系统
2、使用显示器接入服务器,即使远程登陆无法使用,可以直接操作服务器

本次使用措施1进行风险应对。

6.3、处理过程

针对以上的考虑出具如下解决步骤:
1、开启服务器telnet
2、升级软件
由于是多台服务器,使用自动化运维工具ansible工具进行批量操作。

6.3.1、准备工作

6.3.1.1、查看服务

ansible语法

ansible host/ip -m 模块 -a '参数' -i host文件

#常用到的模块
command			远程主机上执行命令,默认模块
shell			远程主机上执行命令,可以支持管道符
setup			收集远程主机的一些信息
copy			本地文件复制到远程主机上
file			设置文件属性
yum				管理安装相关程序包
service			管理服务
group			管理用户组模块
user			管理用户模块
lineinfile		管理远程文件中的内容

查看服务使用到ansible的command模块,command模块为默认模块。

$ ansible jgxt3 -a "rpm -qa telnet-server"		# 查看telnet-server服务
$ ansible jgxt3 -a "rpm -qa xinetd"				# 查看xinetd服务
$ ansible jgxt3 -a "systemctl status telnet"	# 查看telnet服务状态

ansible中command相关参数

chdir			进入到指定目录下,执行命令
creates			指定文件存在时,不执行
removes			指定文件不存在时,不执行
6.3.1.2、创建用户

默认root账号没有telnet权限,使用普通账户relnet远程登陆,如果需要提权,登陆后切换root权限。
创建用户使用到ansible的group和user模块
创建组
创建jgxt用户组

$ ansible jgxt3 -m group -a "name=jgxt state=present"

ansible的group参数

name			组名称
gid				指定组的GID
state			指定组的状态,present-创建组 absent-删除组
system

创建用户
创建jgxt用户

$ ansible jgxt3 -m user -a "name=jgxt state=present groups=jgxt,jgxt shell=/bin/bash append=yes"

ansible-user参数

name			用户名
password		为用户设置密码
update_password	always-只有当密码不相同时才会更新密码,on_create-为新用户设置密码
shell			用户shell设定
groups			用户组设定
home			指定用户家目录
state			状态,present-创建用户,absent-删除用户
append			追加,yes-增量添加group,no-全量变更group,只设置groups指定的group组(默认)
remove			配合state=absent使用,删除用户的家目录-remove=yes
expires			设置用户的过期时间,值是一个时间戳
6.3.1.3、下载软件

创建目录

$ ansible jgxt3 -m file -a "path=/home/tools/telnet owner=jgxt group=jgxt state=directory mode=0644"

ansible-file模块参数

path		必选。用于指定要操作的文件或者目录。
src			当state设置为link或者hard的时候,此参数为链接文件的源文件。
dest		当state设置为link或者hard的时候,此参数为链接文件路径。
force		当state为link的时候,force设置为yes,则就算文件不存在,依旧创建链接文件。
group		设定远程主机目录的组名
mode		设定远程主机文件及目录的权限
owner		设定远程主机目录的用户名
recurse		被操作的文件为目录,将其设置为yes,可递归修改属性。
state
	=directory	如果目录不存在,创建目录
	=file		即使文件不存在,也不会被创建
	=link		创建软链接
	=hard		创建硬链接
	=touch		如果文件不存在,则会创建一个新的文件,如果文件或目录已存在,则更新其最后修改时间
	=absent		删除目录、文件或者取消链接文件

下载软件
软件下载这块为下载到本地,然后通过ansible分发到被控主机
下载本地

创建存储目录
# mkdir -p /home/tools/telnet			
# mkdir -p /home/tools/openssl
# mkdir -p /home/tools/openssh
# 下载telnet软件
# cd /home/tools/telnet
# yum -y install telnet-server --downloadonly --downloaddir ./
# yum -y install xinetd --downloadonly --downloaddir ./
# 下载openssl软件
# cd /home/tools/
# wegt https://ftp.openssl.org/source/openssl-3.0.0.tar.gz
# 下载openssh软件
# wegt https://openbsd.hk/pub/OpenBSD/OpenSSH/portable/openssh-8.8p1.tar.gz

拷贝软件
拷贝软件为主控电脑讲下载的软件批量分发到被控主机上。

$ ansible -m copy -a "src=/home/tools/telnet/xinetd-2.3.15-14.el7.x86_64.rpm dest=/home/tools/telnet/"
$ ansible -m copy -a "src=/home/tools/telnet/telnet-server-0.17-66.el7.x86_64.rpm dest=/home/tools/telnet/"
$ ansible -m copy -a "src=/home/tools/openssl-3.0.0.tar.gz dest=/home/tools/"
$ ansible -m copy -a "src=/home/tools/openssh-8.8p1.tar.gz dest=/home/tools/"

ansible-copy模块

src				与content其一必选。源文件/目录,如果以"/"结尾,复制内容,否则,复制包括目录在内的所有内容。
content			与src其一必选。直接设定目的文件的值,此时dest必须是文件。
dest			必选。远端路径,可以是文件/目录。
backup			覆盖之前备份源文件。yes/no
directory_mode	递归设定目标目录的权限。
follow			支持link文件复制
force			覆盖远程主机不一致的内容
group			设定远程主机目录的组名
mode			设定远程主机文件及目录的权限
owner			设定远程主机目录的用户名

安装依赖库
安装依赖库主要为openssl和openssh依赖库。

新增端口
新增telnet服务使用的端口23

$ ansible jgxt3 -a "systemctl status firewalld"	# 查看防火墙状态
$ ansible jgxt3 -a "firewall-cmd --list-all"	# 查看防火墙开放端口
$ ansible jgxt3 -a "firewall-cmd --zone=public --add-port=23/tcp --permanent"	# 添加23端口
$ ansible jgxt3 -a "firewall-cmd --complete-reload"		# 重新加载防火墙
$ ansible jgxt3 -a "firewall-cmd --query-port=23/tcp"	# 查看23端口状态

6.3.2、开启telnet服务

安装telnet和xinetd程序

$ ansible jgxt3 -m shell -a "chdir=/home/tools/telnet/ rpm -ivh xinetd-2.3.15-14.el7.x86_64.rpm"
$ ansible jgxt3 -m shell -a "chdir=/home/tools/telnet/ rpm -ivh telnet-server-0.17-66.el7.x86_64.rpm"

启动服务
远程启动被控端主机的服务使用到是ansible中的service模块

$ ansible jgxt -m service -a "name=xinetd state=started enabled=yes" -i /etc/ansible/hosts
$ ansible jgxt -m service -a "name=telnet state=started enabled=yes" -i /etc/ansible/hosts

service模块参数

name	服务名称
state	服务状态,startd-启动,stop-停止,restarted-重启,reloaded-重新加载
enabled	服务设置为开机启动项,yes-开机启动,no-开机不启动

查看服务状态

$ ansible jgxt3 -a "systemctl status telnet"
$ ansible jgxt3 -a "systemctl status xinetd"

验证服务
telnet 远程登陆

telnet IP地址

输入创建的账号密码正常登陆即为验证通过。

修改posrgres弱口令 ssh弱口令修复_修改posrgres弱口令

6.3.3、升级软件版本

本次升级主要包括openssl和openssh两个软件。注意安装顺序,先安装openssl,后升级openssh,后者安装需要加载前者的目录程序。

6.3.3.1、备份文件
$ ansible jgxt3 -a 'mv /usr/bin/openssl /usr/bin/openssl_bak'	# 备份openssl文件
$ ansible jgxt3 -a 'rm -rf /etc/ssh/*'	# 删除openssh文件
6.3.3.2、安装openssl

1 安装
配置、编译、安装

$ ansible jgxt3 -m shell -a 'chdir=/home/Downloads/openssl-3.0.0 ./config shared --prefix=/opt/openssl && make && make install'

2 验证安装

$ ansible jgxt3 -a 'echo $?'

输出0表示验证通过
3 创建链接

$ ansible jgxt3 -a 'ln -s /opt/openssl/bin/openssl /usr/bin/openssl'
$ ansible jgxt3 -a 'ln -s /opt/openssl/include/openssl /usr/include/openssl'

4 加载配置

$ ansible jgxt3 -m shell -a 'echo "/opt/openssl/lib64" >> /etc/ld.so.conf'
$ ansible jgxt3 -m shell -a '/sbin/ldconfig'

5 验证安装

$ ansible jgxt3 -a "openssl version"
6.3.3.3、安装openssh

1 安装
配置、编译、安装

$ ansible jgxt3 -m shell -a 'mv /usr/lib/systemd/system/sshd.service /home/service/'
$ ansible jgxt1 -m shell -a './configure --prefix=/opt/openssh --sysconfdir=/etc/ssh  --with-openssl-includes=/opt/openssl/include --with-ssl-dir=/opt/openssl   --with-zlib   --with-md5-passwords   --with-pam  && make && make install'

2 验证安装

$ ansible jgxt3 -a "echo $?"

输出0表示验证通过

3 修改配置

# vim /etc/ssh/sshd_config
$ ansible jgxt3 -m lineinfile -a 'path=/etc/ssh/sshd_config regexp="^#PermitRootLogin yes" line="PermitRootLogin yes" backrefs=yes backup=yes'
$ ansible jgxt3 -m lineinfile -a 'path=/etc/ssh/sshd_config regexp="^#UseDNS yes" line="UseDNS no" backrefs=yes backup=yes'

ansible-lineinfile参数

path		指定文件,必填
line		文本内容
regexp		正则表达式匹配
state		状态,absent-删除,present-操作
backrefs	配合regexp使用,yes-匹配到数据后处理,no-没有匹配到不进行处理
insertafter	文本插入到指定行之后
insertbefore文本插入到指定行之前
backup		是否在修改文件前对文件进行备份
create		操作文件时,文件不存在,是否创建,yes-创建,no-不创建

4 配置文件迁移

# cd /home/tools/openssh-8.8p1
# cp -a contrib/redhat/sshd.init /etc/init.d/sshd
# cp -a contrib/redhat/sshd.pam /etc/pam.d/sshd.pam
# cp /run/systemd/generator.late/sshd.service  /usr/lib/systemd/system/sshd.service

# chmod +x /etc/init.d/sshd 	# 赋权限
# chkconfig --add sshd			# 添加系统服务
# systemctl enable sshd 		# 设置开机启动
# /etc/init.d/sshd start		# 启动服务
# firewall-cmd --reload			# 重启防火墙

5 验证

重启服务器,登陆查看版本

修改posrgres弱口令 ssh弱口令修复_服务器_02

6 关闭telnet服务

# systemctl disable xinetd.servicef	# 禁止xinetd服务
# systemctl stop xinetd.service		# 关闭xinetd服务
# systemctl disable telnet.socket	# 禁止telnet服务
# systemctl stop telnet.socket		# 关闭xinetd服务
# netstat -nltp						# 验证23端口是否关闭
# firewall-cmd --zone=public --remove-port=23/tcp --permanent # 防火墙移除23端口
# firewall-cmd --reload 			# 重新加载防火墙

telnet远程登陆验证

修改posrgres弱口令 ssh弱口令修复_运维_03