网络安全应用安全CLI漏洞扫描【免费下载链接】testssl.shTesting TLS/SSL encryption anywhere on any port项目地址https://gitcode.com/gh_mirrors/te/testssl.sh点击查看免费下载testssl.sh 是一款用于在任意端口上检测 TLS/SSL 加密配置的开源工具其 FAQ.md 集中回答了用户在实际使用中最常遇到的三大类问题运行时行为误报排查、CDN 测试不一致、Docker 下 IPv6 扫描、评分/评级STARTTLS 为何得分低、为何不检测 DNSSEC/MTA-STS以及项目内部架构为什么坚持用 Bash、Bash Sockets 是什么、OpenSSL-bad 二进制的定位。本文以该 FAQ 为骨架结合仓库 testssl.sh 源码、bin/Readme.md 与 Dockerfile.md 等一手资料逐条给出可复现的命令、底层实现证据与设计哲学帮助你排查测试中的疑难现象并理解这些现象背后的原理。一、运行时问题解析1.1 误报排查为什么openssl s_client测不出的问题testssl.sh 却能报出来FAQ 中最常见的疑问是testssl.sh 报出某个发现XYZ但自己用openssl s_client -connect host:port MoreParameters /dev/null却连不上、测不出同样的结果于是怀疑是误报。根因在于测试目标不同。现代操作系统出于安全考虑在编译或默认配置层面禁用了大量不安全特性而 testssl.sh 的使命恰恰相反——它必须有能力去测试那些不安全的密码学配置。为此它采用两条路径向 OpenSSL 传入正确的选项。对当前发行版自带的 OpenSSL你可以临时重新启用部分不安全算法例如openssl s_client -connect host:port -cipher DEFAULTSECLEVEL0 MoreParameters /dev/null使用-cipher DEFAULTSECLEVEL0后可以测出的坏密码学包括NULL-MD5 这类空加密套件、RSASHA1 这类旧签名算法以及 TLSv1 / TLSv1.1 协议。Bash 套接字bash sockets编程。当 OpenSSL 无论如何都无法完成某种连接时testssl.sh 会退回到自实现的套接字通信详见本文 3.2 节。从源码看testssl.sh 会在启动时自动探测当前 OpenSSL 是否支持 SECLEVEL 语法testssl.sh$OPENSSL ciphers SECLEVEL0:ALL /dev/null成功则置HAS_SECLEVELtrue并在构造各种 cipher 参数时自动注入SECLEVEL0:前缀见 testssl.sh 与 testssl.sh从而透明地完成上述坏密码学探测。但有一类坏密码学你无法用这个开关测到古老的 SSL 协议。现代发行版提供的 OpenSSL 二进制要么在源码层面、要么在编译时就把 SSLv2 / SSLv3 禁用了运行时无法重新启用。此时可以借助 testssl.sh 项目提供的OpenSSL-bad 版本二进制OPENSSL_CONF ./bin/openssl.Linux.x86_64 s_client -connect host:port这个二进制启用了 SSLv2、SSLv3 以及更多坏东西但代价是不支持 TLS 1.3也不支持现代椭圆曲线。对于这些能力缺口testssl.sh 会透明地补偿要么用 Bash 实现要么在合适场景自动切换到发行版自带的现代 OpenSSL源码中对应OPENSSL2变量与OSSL_SHORTCUT自动切换机制见 testssl.sh。关于这套预编译二进制的更多细节仓库 bin/Readme.md 做了权威说明它们来自 openssl-1.0.2.bad 分支的编译产物扩展支持 40/56 位密钥、export/ANON 类弱套件、弱 DH 参数、弱 EC 曲线、SSLv2 等常规 OpenSSL/LibreSSL 不具备的脏特性严禁用于生产环境服务端或客户端都不行它们只服务于安全测试。该文档还特别说明随着 Bash Sockets 对弱密码学覆盖能力的增强这些二进制在多数场景已不再是必需品。1.2 透过 CDN / 负载均衡器测试结果为什么不稳定FAQ 指出testssl.sh 总体上是确定性的、可复现的但其测试本质决定了它会打开相当数量的连接。当目标位于 Cloudflare 或各类 CDN、OnPrem 负载均衡器之后时大量连接很容易触发服务端的速率限制rate limit于是不同轮次的测试结果可能不一致——具体表现取决于你是用终端交互测试还是自动化脚本测试是否能看到连接错误也不一定。FAQ 给出的务实建议是如果无法把你测试所用的 IP 加入服务端的白名单allow list可以只运行受限测试例如testssl.sh -P testssl.sh -S或连续运行一系列此类受限测试以降低并发连接数、减少被限流的概率。这两个选项在源码中的含义非常明确testssl.sh-S, --server-defaults只检测服务器默认配置-P, --server-preference只检测服务器的密码套件/协议偏好。相比全量扫描这类单项检查建立的连接数少得多更适合在高限流策略的目标前使用。1.3 用 Docker 镜像扫描 IPv6 / 双栈主机时 IPv6 不通FAQ 明确说明这不是 testssl.sh 的问题而是 Docker 的特性——Docker 在宿主机上默认不会给容器分配 IPv6 地址而且宿主机的路由也可能需要额外配置。最快的修复方式是使用host 网络模式让容器直接复用宿主机的网络栈docker run --rm -ti --nethost drwetter/testssl.sh -6 ipv6.google.com其中-6是 testssl.sh 强制使用 IPv6 的开关IPv6 地址或双栈主机都可用。仓库提供了完整的镜像使用说明Dockerfile.md以及常规非 host 网络的 Docker 运行方式Readme.md例如docker run --rm -ti drwetter/testssl.sh your_cmd_line如果你的 IPv6 扫描场景受限于 Docker 默认网络优先尝试--nethost这是 FAQ 推荐的最短路径。二、评分与评级问题解析2.1 为什么测试 STARTTLS 服务时评分总是偏低FAQ 指出SSLlabs 的评分体系原本就不包含 STARTTLS而 testssl.sh 的评级目标是尽量 1:1 对齐该体系。问题的关键在于 STARTTLS 的工作方式——同一端口上先以明文对话随后由客户端请求升级到 TLS。这种先明文、后升级的模式天然存在嗅探snooping与中间人攻击MitM风险因此项目选择将这类服务标记为不安全并强调只要可能就应该尽量避免使用 STARTTLS。从源码可以印证 testssl.sh 对评级处理的严肃性它实现了完整的评分封顶机制——set_grade_cap()负责把评级封顶到某个等级A/B/C/D/E/F/M/TGRADE_CAP_REASONS数组记录所有封顶原因set_grade_warning()记录评分警告见 testssl.sh 与 testssl.sh。例如源码中有一条硬规则[[ $size -lt 112 || $size None ]] set_grade_cap F Using cipher suites weaker than 112 bitstestssl.sh即密钥强度低于 112 位的套件直接把总分封顶到 F。这种宁可保守、不给虚假安全感的设计取向与 STARTTLS 评分偏低的处理逻辑一脉相承。2.2 你们不做 DNSSEC 和 MTA-STS 检测但这些标准我已经实现了啊FAQ 的回答很直接DNSSEC、MTA-STS 这类机制主要只是为 SMTP 25 端口提供创可贴式补救。具体而言MTA-STS 已有一个待合并的 PRthere is a PR pendingDNSSEC 则尚未列入计划即便服务端配置了这些标准也不能把服务端标为安全——因为每个客户端都需要自行去验证这些标准只要有一个客户端不验证MitM 之门就依然敞开。FAQ 用 SMTP 邮件服务器间通信举例即使服务器证书校验失败邮件仍然会被投递因为邮件送达在默认优先级上高于安全性。换句话说即便收件服务器配置良好、持有有效证书我们也无法判断发件服务器是否在意证书校验——若将其标为安全只会给用户造成虚假的安全感。2.3 那 IMAPS 这类纯 TLS 端口呢FAQ 承认大多数客户端如今确实会做正确的证书校验但强调从明文升级这一机制的缺陷依然存在STARTTLS 注入攻击该缺陷可追溯到 2011 年发现的同类问题Postfix 相关公告编号 CVE-2011-0411以及 Opossum 攻击都属于这类隐患未来还可能有更多衍生问题。因此不能因为多数客户端会校验证书就放松对升级型协议的警惕。补充一个可操作的细节testssl.sh 内置了对大量 STARTTLS 协议族的支持。源码中fd_socket()的对话框分发逻辑覆盖 ftp/smtp/lmtp/pop3/nntp/imap/sieve/ldap/xmpp/postgres/mysql 等协议testssl.sh命令行解析同样接受这些协议名testssl.sh。测试时只需testssl.sh --starttlssmtp host:port另外仓库提供了若干与 STARTTLS 测试调优相关的环境变量供高频测试场景使用testssl.shMAX_STARTTLS_FAIL明文阶段 STARTTLS 握手最大失败次数默认 2、STARTTLS_SLEEP套接字上等待 STARTTLS 的最大秒数默认 10、FAST_STARTTLS默认true以牺牲部分可靠性换取更少的握手次数。三、代码与内部架构问题解析3.1 为什么用 Bash别人都用Python|Golang|Java……FAQ 给出了完整的历史与工程理由历史沿革项目始于 2007 年最初就是一组用于渗透测试的、由 OpenSSL 命令组成的 Shell 脚本。彼时 OpenSSL 是所有连接检查的基础操作所必需的至今部分场景仍然如此用其他语言实现这些操作反而更繁琐。迁移成本随着项目规模膨胀再改写成 Python/Golang/Java 等语言在资源投入上已不现实。调试便利Bash 相比编译型二进制更容易调试。能力被低估testssl.sh 甚至原生包含了对 chacha20、gcm/ccm 等加解密函数的编解码实现见 testssl.sh 中enc-/dec-functions相关代码。FAQ 还强调了一个重要的架构事实如今任意版本支持相关特性的 OpenSSL 或 LibreSSL 都能胜任大部分工作凡是某个特定版本测不了的testssl.sh 就用 Bash 完成即上述编解码函数而连接检查则交给 Bash Sockets。3.2 Bash Sockets 到底是什么Bash Sockets 是一种通过 Shell 接口进行网络编程的方法核心就是 Bash 的虚拟设备文件/dev/tcp/$IPADDRESS/$PORTUDP 场景对应/dev/udp/...。它同样支持 IPv6。在源码中这一机制被封装为fd_socket()函数testssl.sh其核心动作是exec 5/dev/tcp/$nodeip/$PORT即通过文件描述符 5 建立双向 TCP 连接。几个值得注意的实现细节对 IPv6 地址函数会先剥掉方括号tr -d []因为套接字写法不需要方括号支持通过 HTTP 代理CONNECT 方法建连并会解析代理返回的 HTTP 状态行判断是否成功testssl.sh支持套接字超时控制当设置了SOCKET_TIMEOUT时用timeout命令在子 Shell 中执行连接超时计入NR_SOCKET_FAIL超过MAX_SOCKET_FAIL默认 2则终止testssl.sh建连成功后按 STARTTLS 协议分发到starttls_ftp_dialog、starttls_smtp_dialog、starttls_imap_dialog等各协议对话框函数。仓库中还有多处独立的/dev/tcp用法如 testssl.sh、testssl.sh用于探测端口可达性等场景。3.3 那为什么不用Python|Perl|Golang|Java单独实现某个更快的函数FAQ 点出了项目的核心哲学与卖点testssl.sh 的哲学与美在于它在任何地方都能运行runs everywhere与操作系统无关且只依赖最小集合的典型 Unix 工具加上任意 Bash 和任意 OpenSSL 版本。这意味着用户不需要担心某个版本的依赖库没装、二进制版本是 A.b、解释器版本是 C.d…… 这种零额外依赖、随处可跑的独立性正是项目坚持 Bash 的重要原因。3.4 关于 OpenSSL-bad会不会回移 TLS 1.3 / QUIC二进制的信息去哪看FAQ 给出两个明确的官方答复不会回移 TLS 1.3、QUIC 或其他现代密码学到 OpenSSL-bad 版本。因为更高效的做法是使用发行版自带的现代 OpenSSL再用 OpenSSL-bad 或 Bash Sockets 按需补偿其缺失能力。同时除非天塌下来否则不会再编译出另一套二进制。OpenSSL-bad 的源码、文档与许可证可在其独立的 openssl-1.0.2.bad 仓库获取仓库 bin/Readme.md 亦说明这些二进制编译自该分支。欢迎将其用于测试但不要在生产环境的服务器或客户端中使用。仓库 bin/ 目录当前实际提供的预编译二进制包括openssl.Linux.x86_64openssl.FreeBSD.amd64openssl.Darwin.x86_64另有许可证与版本信息文件OPENSSL-LICENSE.txt、openssl-Vall.txt。bin/Readme.md 同时提醒这些二进制不支持 TLS 1.3、缺少较新的 TLS 1.2 套件且随着弱密码学场景逐渐由 Bash Sockets 覆盖它们在未来版本中可能被退役。四、FAQ 关键结论速查问题类别关键结论可复现命令 / 源码依据误报排查现代 OpenSSL 默认禁用不安全特性需SECLEVEL0临时启用openssl s_client -connect host:port -cipher DEFAULTSECLEVEL0 /dev/nulltestssl.shSSLv2/SSLv3 测试发行版二进制编译时禁用需 OpenSSL-badOPENSSL_CONF ./bin/openssl.Linux.x86_64 s_client -connect host:portbin/Readme.mdCDN/负载均衡结果抖动连接过多触发服务端限流改用受限测试testssl.sh -P、testssl.sh -Stestssl.shDocker 下 IPv6 不通Docker 默认不给容器分配 IPv6改用 host 网络docker run --rm -ti --nethost drwetter/testssl.sh -6 ipv6.google.comDockerfile.mdSTARTTLS 评分低明文先行升级天然不安全评分体系未覆盖 STARTTLS评级封顶机制 testssl.sh为何不用其他语言2007 年起源于 OpenSSL 命令脚本随处运行、最小依赖是核心哲学FAQ.mdBash Sockets通过/dev/tcp/$IP/$PORT实现网络编程支持 IPv6 与代理testssl.shOpenSSL-bad 定位不回移 TLS 1.3/QUIC仅供测试严禁生产使用bin/Readme.md以上答案均以仓库当前版本的源码、文档与二进制为事实依据如果你遇到 FAQ 未覆盖的新现象建议先对照 CHANGELOG.md 确认版本行为差异再决定是否提交 issue。赞分享网络安全应用安全CLI漏洞扫描【免费下载链接】testssl.shTesting TLS/SSL encryption anywhere on any port项目地址https://gitcode.com/gh_mirrors/te/testssl.sh点击查看免费下载相关推荐s3git完全指南如何将Git版本控制带入S3云存储的终极方案s3git完全指南如何将Git版本控制带入S3云存储的终极方案 s3git是一款革命性的分布式版本控制系统它将Git的强大版本管理能力与S3云存储的无限扩展Falco架构深度剖析内核监控与容器运行时集成原理Falco架构深度剖析内核监控与容器运行时集成原理 Falco作为CNCF毕业项目通过内核级监控与容器运行时集成为Kubernetes集群提供实时安全事件云原生运行时防护IDS应用安全RivetKit 运行时边界解析NAPI 原生与 WASM 双运行时的架构约束与实现原理RivetKit 运行时边界解析NAPI 原生与 WASM 双运行时的架构约束与实现原理 导读 RivetKit 是 Rivet Actors 的原生 SDK后端AI Agent人工智能流程编排WebSocket上一篇Powerlevel10k 图标不显示三步修好字体与 localePowerline 符号快速完整恢复下一篇osquery 部署与运维调试完全指南verbose 模式、配置校验、Watchdog 与数据库排障创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
