1. 为什么在Kali里折腾SSH和防火墙值得单独写一篇很多人第一次在Kali上开SSH都是被逼的。要么是虚拟机里敲命令太憋屈想用宿主机终端连进去要么是手头只有一台笔记本想把Kali当远程跳板机跑扫描任务要么是实验室里几台机器要互传文件懒得插U盘。结果一上手就发现Kali的SSH默认状态跟Ubuntu、CentOS完全不是一回事——服务没起、端口没开、防火墙规则还跟你想的不一样。我见过太多人卡在“Connection refused”或者“Permission denied”上折腾一晚上最后放弃继续在虚拟机窗口里一个字一个字地敲。这篇东西就是把我自己反复踩过的坑、验证过的配置流程以及那些文档里不会写的细节一次性讲清楚。核心就三件事怎么把SSH服务跑起来、怎么让防火墙放行、怎么让配置在重启后依然生效。听起来简单但每一步都有坑。比如Kali Rolling版本默认不带SSH服务端你得先装比如UFW和iptables在Kali里的默认策略跟Debian系其他发行版有微妙差异再比如你改了sshd_config之后忘了检查语法服务直接起不来连报错都看不懂。适合谁看如果你是刚接触Kali的新手照着做能少走两小时弯路如果你已经用过SSH但总在防火墙这关卡住这里有针对Kali的排查链路如果你是要在实验环境里批量配置多台Kali后面也有可复用的配置模板和批量操作思路。我不讲那些“SSH是加密远程登录协议”的教科书定义直接上操作、上原理、上我踩过的坑。2. Kali里SSH服务的安装与首次启动2.1 先确认你的Kali到底有没有SSH服务端很多人上来就systemctl start ssh然后报错“Unit ssh.service not found”。这不是命令错了是Kali默认根本没装SSH服务端。Kali的定位是渗透测试发行版默认只装了SSH客户端让你去连别人服务端让别人连你需要手动安装。这个设计逻辑跟Ubuntu Server完全相反所以习惯Ubuntu的人第一次用Kali会懵。确认方法很简单两条命令# 查看ssh服务端是否安装 dpkg -l | grep openssh-server # 查看ssh客户端是否安装这个默认一定有 dpkg -l | grep openssh-client如果第一条命令没有任何输出说明服务端没装。第二条命令应该能看到openssh-client的包信息。这里有个细节Kali Rolling版本在2020年之后的镜像里连客户端都可能精简掉但大多数场景下客户端是保留的因为渗透测试经常要SSH连靶机。注意不要用apt install ssh这个命令。ssh是一个元包在不同发行版里指向不同东西。在Kali里直接装openssh-server最稳妥避免装错包。2.2 安装openssh-server的正确姿势安装本身不复杂但有几个前置动作容易被忽略。首先更新源Kali的源如果没配好安装会失败或者装到旧版本sudo apt update sudo apt install openssh-server -y装完之后系统会自动生成主机密钥host keys这些密钥在/etc/ssh/目录下文件名类似ssh_host_rsa_key、ssh_host_ecdsa_key。如果你之前手动删过这些文件或者从别的机器克隆了Kali镜像密钥可能冲突导致客户端连接时报“Host key verification failed”。解决办法是删掉/etc/ssh/ssh_host_*然后重新生成sudo rm /etc/ssh/ssh_host_* sudo dpkg-reconfigure openssh-server这个dpkg-reconfigure命令会重新跑一遍配置脚本自动生成新的主机密钥。我试过在克隆的虚拟机里直接启动SSH客户端连上去报密钥不匹配排查了半天才发现是克隆导致密钥重复。这个坑在批量部署Kali虚拟机的时候特别常见。2.3 启动服务并设置开机自启装完之后SSH服务默认可能是disabled状态。Kali用的是systemd所以操作很标准# 启动服务 sudo systemctl start ssh # 设置开机自启 sudo systemctl enable ssh # 查看状态 sudo systemctl status ssh状态输出里看到active (running)就说明服务跑起来了。但这里有个隐藏问题Kali在某些版本里ssh.service和ssh.socket是两套机制。如果你用systemctl status ssh看到的是socket激活模式那服务可能不是常驻的而是按需启动。对于实验环境我建议统一用ssh.service避免socket模式带来的端口监听延迟。检查方法sudo systemctl is-enabled ssh sudo systemctl is-active ssh两个命令分别返回enabled和active才算配置到位。如果is-enabled返回disabled即使当前跑着重启后也会失效。2.4 验证SSH是否真的在监听服务状态显示running不代表端口一定在监听。可能配置文件有语法错误服务启动了但没绑定端口。用这条命令确认ss -tlnp | grep :22或者老一点的系统用netstat -tlnp | grep :22。输出里应该看到LISTEN状态和对应的进程名sshd。如果什么都没看到说明服务虽然显示running但实际没监听端口这时候要去查/var/log/auth.log或者journalctl -u ssh看具体报错。我遇到过一种情况sshd_config里写了Port 2222但防火墙只开了22结果本地ss能看到2222在监听但远程连不上。所以端口监听和防火墙放行是两件事必须分开验证。3. sshd_config里那些真正影响连接的参数3.1 默认配置里哪些参数必须改Kali的/etc/ssh/sshd_config默认配置其实挺保守的但有几个参数在实际使用中会带来麻烦。我按重要性排个序参数默认值建议值原因PermitRootLoginprohibit-passwordno禁止root直接登录用普通用户sudoPasswordAuthenticationyes按需实验环境可保留yes生产环境建议noPubkeyAuthenticationyesyes密钥登录更安全保留Port22按需改非标准端口可减少扫描噪音ListenAddress0.0.0.0按需多网卡时指定监听地址PermitRootLogin这个参数特别值得说。Kali默认是prohibit-password意思是root不能用密码登录但可以用密钥。很多人改成yes图方便结果实验环境被扫到就麻烦。我的建议是保持no用普通用户登录后再sudo -i切root多一步但安全很多。3.2 改完配置必须做的语法检查这是我最想强调的一点改完sshd_config千万不要直接restart。先跑语法检查sudo sshd -t如果配置有问题这条命令会直接告诉你哪一行错了。没有输出就说明语法OK。我见过太多人改完配置直接systemctl restart ssh结果服务起不来SSH断了只能去虚拟机控制台救火。先检查再重启这个习惯能省你很多时间。检查通过后再重启sudo systemctl restart ssh重启后再次用ss -tlnp确认端口监听正常然后用另一台机器或另一个终端尝试连接。不要关掉当前SSH会话再重连万一新配置有问题你至少还有一个活着的会话可以回滚。3.3 密钥登录的配置细节密码登录虽然方便但在实验环境里经常被扫描器爆破。配密钥登录其实不复杂但有几个细节容易漏。生成密钥对在客户端机器上操作ssh-keygen -t ed25519 -C kali-labed25519比RSA更短更快现代系统都支持。生成后把公钥传到Kali上ssh-copy-id -i ~/.ssh/id_ed25519.pub userkali-ip如果ssh-copy-id不可用手动追加也行cat ~/.ssh/id_ed25519.pub | ssh userkali-ip mkdir -p ~/.ssh chmod 700 ~/.ssh cat ~/.ssh/authorized_keys chmod 600 ~/.ssh/authorized_keys这里权限很关键。~/.ssh必须是700authorized_keys必须是600。权限不对的话SSH会静默忽略密钥只让你输密码而且不报错。我排查过好几次“密钥明明传了但还是要密码”的问题最后都是权限不对。服务端这边确认sshd_config里PubkeyAuthentication yes AuthorizedKeysFile .ssh/authorized_keys改完记得sshd -t检查再重启。3.4 监听端口和地址的取舍默认监听0.0.0.0:22意思是所有网卡的所有IP的22端口都接受连接。在实验环境里如果你的Kali有多张网卡比如NAT一张、Host-Only一张可能只想让Host-Only那张接受SSH。这时候改ListenAddressListenAddress 192.168.56.10 Port 22这样只有指定IP的22端口监听NAT网卡那边就连不上了。这个配置在隔离实验环境里很有用避免暴露到不该暴露的网络。改端口的话注意SELinuxKali默认没开和防火墙都要同步改。我一般不建议改端口因为Kali的实验环境通常在内网改端口带来的安全收益有限反而增加配置复杂度。如果确实要改记得sshd -t检查防火墙规则同步更新。4. Kali防火墙的默认状态与放行策略4.1 Kali默认防火墙到底开没开这是最容易让人困惑的地方。Kali默认没有启用任何防火墙。ufw status会显示inactiveiptables -L会显示空规则链。也就是说刚装好的Kali所有端口都是开放的SSH只要服务跑起来就能连。但问题在于很多人从别的教程里抄了ufw enable结果把自己关在外面。因为UFW默认策略是deny incoming你一启用所有入站连接全断包括你正在用的SSH。如果你是在远程连Kali启用UFW的瞬间你就掉线了。所以第一步永远是先确认防火墙状态再决定要不要动它。sudo ufw status verbose sudo iptables -L -n如果ufw是inactiveiptables是空规则那SSH连不上就不是防火墙的问题去查服务监听和网络连通性。4.2 UFW的规则配置与SSH放行顺序如果你确实需要启用防火墙比如Kali放在公网可访问的环境那顺序必须是先放行SSH再启用UFW。# 先放行SSH端口 sudo ufw allow 22/tcp # 再启用 sudo ufw enable如果SSH改过端口比如2222sudo ufw allow 2222/tcp sudo ufw enable启用后检查规则sudo ufw status numbered输出里应该看到22/tcp ALLOW IN Anywhere。如果没看到说明规则没生效检查是不是先enable后allow了。注意如果你已经启用了UFW并且SSH断了别慌。去虚拟机控制台VMware/VirtualBox的窗口登录然后sudo ufw allow 22/tcp再sudo ufw reload。如果控制台也进不去重启进恢复模式ufw disable。4.3 iptables直接操作的场景有些实验环境要求用iptables而不是UFW比如你要模拟特定网络策略。iptables的规则是即时生效的但默认重启后丢失。要持久化得用iptables-persistentsudo apt install iptables-persistent -y放行SSH的规则sudo iptables -A INPUT -p tcp --dport 22 -j ACCEPT sudo iptables -A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT第二条规则很重要它允许已建立的连接继续通信。没有这条你SSH连上去之后回包可能被拦表现为能连上但卡死。保存规则sudo netfilter-persistent save这个命令会把当前iptables规则写到/etc/iptables/rules.v4重启后自动加载。4.4 UFW和iptables的优先级关系这里有个容易搞混的点UFW底层就是iptables的前端。你ufw allow之后实际是在iptables里插了规则。如果你同时手动改iptables可能跟UFW的规则冲突。我的建议是二选一要么全用UFW要么全用iptables不要混着来。如果非要混用记住UFW的规则链在iptables里是ufw-user-input你手动加的规则如果在INPUT链里排在UFW之前可能覆盖UFW的策略。排查的时候用iptables -L -n --line-numbers看规则顺序顺序错了就全乱。5. 从连接失败到连通的完整排查链路5.1 第一层网络通不通SSH连不上先别急着查SSH配置。第一步永远是确认网络层通不通ping kali-ip如果ping不通后面都不用查了。检查Kali的IP、网卡模式NAT/桥接/Host-Only、宿主机防火墙。虚拟机环境里最常见的是网卡模式选错比如Kali是NAT模式但你从宿主机用Host-Only的网段去连肯定不通。ping通了但SSH连不上继续下一步。5.2 第二层端口开没开在Kali本机确认端口监听ss -tlnp | grep :22有输出说明服务在监听。没输出说明SSH服务没跑起来回去查systemctl status ssh和journalctl -u ssh。本机确认监听正常后从客户端测端口连通性nc -zv kali-ip 22或者用telnet kali-ip 22。如果显示Connection refused说明端口没监听或者防火墙REJECT。如果显示Connection timed out说明防火墙DROP或者网络中间有设备拦截。5.3 第三层防火墙规则有没有拦在Kali上查防火墙sudo ufw status verbose sudo iptables -L -n -v重点看INPUT链的默认策略和规则。如果默认策略是DROP且没有放行22的规则那就是防火墙拦了。加规则sudo ufw allow 22/tcp或者iptablessudo iptables -I INPUT -p tcp --dport 22 -j ACCEPT注意-I是插入到链首-A是追加到链尾。如果前面有DROP规则-A加的规则永远匹配不到必须用-I。5.4 第四层SSH服务本身的认证问题端口通了但连接时报Permission denied或者Authentication failed那就是认证层的问题。常见原因密码错了大小写、键盘布局用户不存在或被锁定sshd_config里AllowUsers或DenyUsers限制了密钥权限不对PAM模块拦截排查方法在Kali上看/var/log/auth.log里面会记录每次登录尝试的详细原因。比如Failed password for invalid user说明用户名错了Authentication refused: bad ownership or modes说明密钥文件权限不对。5.5 第五层那些诡异的“能连上但卡住”有一种情况最折磨人SSH能连上输入密码后卡住或者连上后命令执行很慢。这通常是DNS反向解析导致的。sshd_config里有个UseDNS参数默认可能是yes服务端会尝试反向解析客户端IP如果DNS不可用就会卡几十秒。解决办法UseDNS no GSSAPIAuthentication no改完sshd -t检查再重启。这两个参数在实验环境里建议都关掉能显著提升连接速度。6. 让配置在重启后依然生效的持久化方案6.1 SSH服务自启的确认systemctl enable ssh只是设置了开机自启但如果你用的是ssh.socket模式可能行为不一样。确认方法systemctl list-unit-files | grep ssh输出里ssh.service应该是enabled。如果是disabled重新enable。另外检查有没有ssh.socket被enable了如果两个都enable可能冲突。建议只保留ssh.servicesudo systemctl disable ssh.socket sudo systemctl enable ssh.service6.2 防火墙规则的持久化UFW的规则默认就是持久的ufw enable之后规则会写到/etc/ufw/下的配置文件重启自动加载。但有个例外如果你手动改了/etc/ufw/user.rules但没ufw reload重启后可能不生效。保险做法是每次改完规则跑一次sudo ufw reloadiptables的话前面说了用netfilter-persistent save。但注意如果你同时装了UFW和iptables-persistent重启时可能互相覆盖。建议只用一个。6.3 配置文件备份与版本管理sshd_config改多了容易乱建议改之前备份sudo cp /etc/ssh/sshd_config /etc/ssh/sshd_config.bak如果实验环境有多台Kali可以把调好的配置存到版本控制里批量分发。我自己的做法是维护一个sshd_config模板新机器装好SSH后直接覆盖然后sshd -t检查重启服务。这样能保证所有机器的配置一致排查问题的时候少一个变量。6.4 重启后的验证清单每次重启Kali后按这个清单过一遍systemctl status ssh— 服务是否runningss -tlnp | grep :22— 端口是否监听sudo ufw status— 防火墙规则是否加载从客户端nc -zv kali-ip 22— 端口是否可达实际SSH登录一次 — 认证是否正常这五步走完基本能覆盖99%的“重启后连不上”问题。我见过太多人重启后直接连连不上就慌其实按清单一步步查问题很快定位。7. 多场景下的配置取舍与经验心得7.1 虚拟机NAT模式下的SSH配置NAT模式下Kali的IP是VMware/VirtualBox分配的宿主机不能直接访问需要配端口转发。以VirtualBox为例在虚拟机设置里加一条NAT端口转发规则宿主端口2222虚拟机端口22。然后从宿主机ssh -p 2222 user127.0.0.1就能连上。这种场景下Kali内部的防火墙通常不用动因为NAT转发是在虚拟化层做的流量到了Kali内部已经是本地连接。但如果你在Kali里启用了UFW且没放行22照样连不上。所以NAT模式下SSH服务跑起来UFW放行22两个条件缺一不可。7.2 桥接模式下的局域网访问桥接模式下Kali跟宿主机在同一局域网IP是路由器分配的。这种场景最方便同网段任何机器都能SSH连。但要注意如果局域网有DHCPKali的IP可能变建议配静态IP或者在路由器上绑MAC防火墙必须放行22因为流量是从外部进来的如果局域网有安全策略可能拦截22端口换个端口试试桥接模式下我一般会改SSH端口到非标准值减少被扫描的概率。虽然实验环境通常安全但养成习惯没坏处。7.3 多台Kali批量配置的思路如果你要配多台Kali比如实验集群一台台手动改太慢。我的做法是写个简单的shell脚本把sshd_config模板、防火墙规则、密钥分发都自动化。核心步骤用sshpass或预置密钥做初始认证分发sshd_config模板跑sshd -t检查重启服务配置UFW规则验证端口监听这个脚本不需要多复杂几十行就能搞定。关键是每步都要有错误检查比如sshd -t失败就中止不要盲目重启。7.4 那些文档里不会写的细节最后分享几个我踩过的坑坑一sshd_config里的注释符号。#开头的行是注释但有些参数默认值就是注释掉的。你改的时候如果直接在注释行后面加内容比如#Port 22改成#Port 22然后另起一行写Port 2222没问题。但如果你把#去掉改成Port 22又没改端口号那就跟默认一样。改配置的时候看清楚是注释还是生效行。坑二UFW的allow和limit。ufw allow 22是允许所有连接ufw limit 22是限制连接频率防爆破。实验环境用allow就行limit在某些扫描场景下会误拦。坑三SSH连接慢但能连上。除了UseDNS还可能是GSSAPIAuthentication导致的。两个都关掉连接速度立竿见影。坑四改了端口后ss -tlnp看不到。检查sshd_config里是不是有多个Port行或者ListenAddress限制了。sshd -t能查出语法问题但逻辑问题得自己看。坑五密钥登录突然失效。检查~/.ssh和authorized_keys权限检查sshd_config里PubkeyAuthentication是不是被注释了检查AuthorizedKeysFile路径对不对。这三个查完基本能解决。这些细节在官方文档里要么一笔带过要么分散在不同章节实际用的时候得自己串起来。我写这篇就是想把这条链路一次性打通让你在Kali上开SSH、配防火墙这件事上不再卡壳。
阅读完成 · 觉得有帮助?