ChrootDirectory路径权限不对、ForceCommand未生效、用户仍能cd..或执行ssh命令,根本原因是未同时满足三个硬性条件:ChrootDirectory及其所有上级目录属主必须为root、权限不能含组/其他写位、必须启用internal-sftp并强制ForceCommand接管。

ChrootDirectory 路径权限不对、ForceCommand 没生效、用户仍能 cd .. 或执行 ssh 命令——这些问题基本都源于三个硬性条件没同时满足:路径属主必须是 root、路径权限不能含组/其他写位、internal-sftp 必须启用且强制接管。
ChrootDirectory 的权限和属主为什么必须是 root:root?
OpenSSH 在启动 chroot 时会主动检查 ChrootDirectory 及其所有上级目录(直到 /)的属主和权限。只要其中任意一级不是 root 所有,或权限包含组/其他可写(比如 775、777),sshd 就会拒绝加载该配置,日志里通常报错:fatal: bad ownership or modes for chroot directory component。
实操建议:
-
ChrootDirectory(如/sftp/john)必须执行:sudo chown root:root /sftp/john+sudo chmod 755 /sftp/john - 它的父目录(如
/sftp)也得是root:root且755;/当然没问题,但中间任何一层漏了都会失败 - 用户真正能读写的目录(如
/sftp/john/upload)要放在 chroot 内部,再单独chown john:john和chmod 755或775
Match 块位置和 ForceCommand 怎么避免被绕过?
如果 Match User john 块写在 Subsystem sftp internal-sftp 之前,或者写在全局 Match 块之后,OpenSSH 可能忽略它;更关键的是,不加 ForceCommand internal-sftp,用户用 ssh john@host 仍可能拿到一个空 shell(哪怕 /sbin/nologin),甚至通过 scp 或 rsync over ssh 绕过限制。
Linux 性能分析与调优专家,覆盖 CPU、内存、磁盘 I/O、网络、内核参数、编译优化、容器/K8s。适用场景:系统卡顿/高负载、内存不足/OOM/Swap 高、CPU 异常/iowait 高。
实操建议:
-
Subsystem sftp internal-sftp必须取消注释,且不能和旧的sftp-server行共存 -
Match User john块必须放在sshd_config文件末尾、所有其他Match块之后(OpenSSH 按顺序匹配,先匹配到就停) - 务必包含这三行:
ForceCommand internal-sftp、AllowTcpForwarding no、X11Forwarding no - 用户 shell 设为
/usr/sbin/nologin或/bin/false,但仅靠这个不够,ForceCommand才是真正拦截点
用户上传失败:/sftp/john 下没有写权限怎么办?
因为 /sftp/john 自身必须 chown root:root 且不可写,用户自然无法直接在根目录下 put。这不是 bug,是 chroot 安全模型的设计前提。
实操建议:
- 在
/sftp/john内创建子目录,例如:sudo mkdir /sftp/john/upload - 把子目录所有权交给用户:
sudo chown john:john /sftp/john/upload - 权限设为
755(用户可写,组/其他只读)或775(若需组协作);不要用777,没必要也不安全 - 用户登录后默认位于
/(即/sftp/john),需先cd upload才能上传
sshd_config 后,必须用 sudo systemctl restart sshd(不是 reload),否则部分配置(尤其是 Match 块)不会重新加载;而且每次改完最好用 sudo sshd -t 检查语法,避免配错导致 SSH 服务中断。

















