5个版本 (3个主要版本变更)
新版本 4.0.0 | 2024年8月23日 |
---|---|
3.0.0 | 2024年7月30日 |
2.0.0 | 2024年7月18日 |
1.1.0 | 2024年7月7日 |
0.0.0 |
|
在网络编程中排名153
每月下载量207次
84KB
1.5K SLoC
letmein - 认证端口敲击
Letmein是一款具有简单且安全认证机制的简单端口敲击工具。它可以用于增强SSH、VPN、IMAP等服务对预认证攻击的防御。
Letmein通过敲击认证屏障隐藏服务器上的服务,以减少服务的攻击面。除非敲击认证成功,否则服务不可访问。在敲击成功的情况下,letmeind服务器只为执行敲击的客户IP地址打开被敲击的端口。具有不同IP地址的机器仍然无法访问受保护的服务。
无法成功认证敲击序列的机器无法访问受保护的服务。它们将在受保护服务端口上收到TCP/ICMP reject
,如下面的示例 nftables.conf
所示。(您也可以选择在您的 nftables.conf
中 drop
数据包)。
Letmein需要一个基于 nftables
的防火墙。它不与 iptables
一起工作。如果您使用基于 iptables
的防火墙,请在安装letmein之前将其转换为 nftables
。有关如何进行的描述可以在互联网上找到。这并不像听起来那么困难,也不需要那么多工作。 :)
典型的letmein操作流程
项目链接
使用示例:将OpenSSH (sshd) 访问放在敲击认证屏障后面
在服务器上安装letmein服务器软件(请参阅下面的部分)。
在客户端安装letmein客户端软件(请参阅下面的部分)。
请阅读该项目提供的nftables.conf示例配置文件。需要在现有的nftables
配置中添加一个letmein特定的输入链。请相应地修改您的nftables.conf
文件。
使用以下客户端命令生成共享密钥和用户标识符,这些将被安装到服务器和客户端上
letmein gen-key -u 00000000
gen-key命令将生成的密钥字符串打印到控制台。默认情况下,这将为用户标识符00000000
生成一个安全的随机密钥。您可以手动编辑用户标识符,如果需要,也可以保持原样。
将生成的字符串(用户标识符和共享密钥)添加到服务器配置文件/opt/letmein/etc/letmeind.conf
中。将生成的密钥字符串与用户标识符一起放入配置文件的[KEYS]
部分。
将相同的生成的字符串(用户标识符和共享密钥)添加到客户端配置文件/opt/letmein/etc/letmein.conf
中。将生成的密钥字符串与用户标识符一起放入配置文件的[KEYS]
部分。
在服务器中创建一个resource
来描述可以打开的sshd
端口。在服务器配置文件/opt/letmein/etc/letmeind.conf
的[RESOURCES]
部分中,必须指定所有可能打开的端口。一个资源由一个资源标识符后跟一个端口标识符组成,例如
[RESOURCES]
00000022 = port: 22
资源标识符是一个8位十六进制数字。在这个例子中是22(hex),但它可以是任何数字。它只需要在服务器和客户端上相同即可。在port:
之后指定可以敲开的端口号(十进制)。
将相同的资源以及相同的资源标识符和端口号添加到客户端配置文件/opt/letmein/etc/letmein.conf
中。
重新启动letmein服务器
systemctl restart letmeind.service
现在从您的nftables.conf
防火墙配置中删除静态的sshd
端口(22)accept
。在成功的敲击认证后,Letmein将动态地将此类规则安装到Letmein输入链中。然后重新启动nftables
systemctl restart nftables.service
完成!现在您应该能够打开服务器上的sshd
端口
# This must fail! No successful knock authentication, yet.
# If this does not fail, check if you have removed the sshd accept rule from nftables.conf.
ssh your-server.com
# Knock-open port 22 (sshd) on the server using user-id/key 00000000:
# (You do not have to specify -u 00000000 if that is your default user (see config).)
letmein knock -u 00000000 your-server.com 22
# Now you should be able to ssh into your server successfully:
ssh your-server.com
要自动在连接ssh之前敲击端口,您可以在您的~/.ssh/config
文件中添加一个Match exec
规则
Match host your-server.com exec "letmein knock -u 00000000 your-server.com 22"
先决条件
必须安装Rust编译器来构建letmein。建议使用最新的稳定版Rust编译器
Rust安装程序将安装编译器和构建工具cargo
。
构建需要安装额外的cargo-audit
和cargo-auditable
工具。运行以下命令安装这两个工具
cargo install cargo-audit cargo-auditable
在运行时,需要安装并可在$PATH
中访问的nftables nft
二进制文件。在Debian上,请安装nftables
包
apt install nftables
构建letmein
运行build.sh
脚本以构建letmein。
安装所有构建必备条件后,运行构建脚本
./build.sh
安装letmein
安装客户端
然后运行 install-client.sh
来将 letmein 客户端安装到 /opt/letmein/
./install-client.sh
客户端用于向服务器发送敲击数据包。
安装服务器
为服务器准备用户和组
letmein 服务器面向公共网络的部分以降低权限运行,以减少攻击面。
为此,用户 letmeind
和组 letmeind
必须存在于 /etc/passwd
和 /etc/group
中。建议此用户不要有 shell 和家目录分配,因此不是登录用户。
您可以使用以下辅助脚本在您的系统中创建用户和组
./create-user.sh
安装服务器和 systemd 单元
在构建并创建 letmeind
系统用户后,运行 install-server.sh
来将 letmeind 服务器安装到 /opt/letmein/
./install-server.sh
安装服务器还会将服务和服务套接字安装到 systemd 并启动 letmeind 服务器。
服务器用于接收来自客户端的敲击数据包。在敲击认证成功后,服务器将在其 nftables
防火墙中打开被敲击的端口。
平台支持
客户端
客户端应用程序 letmein
是可移植的,应在所有主要平台上运行。测试过的平台包括
- Linux
- Android,在 Termux 上
- Windows
- MacOS(仅测试构建)
服务器
服务器应用程序 letmeind
仅支持 Linux,因为它仅支持 nftables
作为防火墙后端。
安全注意:用户标识符和资源标识符
请注意,来自配置文件的用户标识符和资源标识符在网络上以明文形式传输,未加密。
确保用户标识符和资源标识符不包含任何私人信息。
这些标识符仅用于对不同的 letmein
密钥、安装和配置进行抽象标识。
内部结构和设计目标
letmein 的主要设计目标是
- 它使用内存安全的编程语言实现,使得某些严重错误的类别变得不可能。
- 算法和实现尽可能简单。
- 它不实现复杂的加密算法,如非对称的公钥/私钥加密。它使用共享密钥与 HMAC/SHA3 进行身份验证。
- 它具有重放保护。重放敲击数据包序列不会导致身份验证成功。
- 它只为发起敲击请求的 IP 地址打开端口。默认情况下,对于 IPv4 和 IPv6 都是这样,如果可用。此行为可以通过客户端命令行选项
-4
和-6
进行调整。 - letmein 不链接到用不安全语言编写的库 (.so),除非是操作系统或 Rust 编译器所必需的。唯一的动态链接库是
- libc.so
- libm.so
- libgcc_s.so
- linux-vdso.so
- ld-linux-*.so
- ld-android.so(仅限 Android)
- libdl.so(仅限 Android)
- libarmmem-*.so(仅限 Raspberry Pi)
安全分析
据我所知,该程序已被精心设计以实现安全。
然而,没有人是不犯错误的。
- 请阅读代码并对其进行评论。
- 如果您有任何问题、建议或请求,请随时提交一个issue。
- 请讨论设计决策的优缺点。
我很乐意听听您的意见。
如果您发现了一个安全漏洞,请参阅漏洞报告流程了解如何操作。
已知弱点
letmein存在一些已知的弱点。在本段中,我们将讨论这些弱点存在的原因。
这些弱点没有被letmein的设计考虑在内,以简化设计。这是简单设计和实际不影响安全性的弱点之间的权衡。
人们认为这些弱点不会使letmein在实际使用中变得不安全。简单的目标是减少攻击面,从而提高安全性。
-
弱点:用户标识符和资源标识符从配置中传输时,以纯文本形式在网络中传输。
- 理由:用户标识符和资源标识符不应包含私人或机密信息。
-
弱点:第一个
Knock
包没有针对重放攻击的保护。- 理由:确实,攻击者可以成功重放
Knock
包。但这并不意味着太多。攻击者仍然无法成功地解决Challenge
。Knock
的认证只是存在,因为它在当前的设计中易于实现,并且可以阻止没有密钥的端口敲击。
- 理由:确实,攻击者可以成功重放
-
弱点:在合法用户成功敲击序列后,如果中间人攻击者能够使用与合法用户相同的发送者IP地址,则可以使用被敲开的端口。
- 理由:letmein仅验证敲击序列期间发生的事情。一旦防火墙为IP地址打开,敲击序列之后发生的事情完全超出letmein的范畴。然而,敲击序列成功后,端口保持打开的时间有限。敲击序列完成后,中间人使用它的时间非常有限。
-
弱点:如果您在NAT后面敲开一个端口,那么该端口将为整个NAT网络打开,因为从外部看,NAT网络只有一个IP地址。NAT网络内的人都可以访问被敲开的端口。
- 理由:端口只开放了短暂和有限的时间,并且预期会有第二层安全(见下文的2FA讨论)。虽然端口将打开整个NAT网络是不幸的事实,但这仍然比没有端口敲击(在整个互联网上打开)要好得多。
-
弱点:认证密钥是一个存储在服务器和客户端上的共享机密。
- 原因:确实,能够成功接管服务器或客户端的攻击者可以窃取密钥并验证未来的会话。这是在实现复杂的公私钥密码学、letmein旨在保护的总体目标与设计的简单性之间的权衡。letmein 不 应该保护其他未受保护的服务。它只应该是一个已安全系统中的 额外 安全屏障。将其视为 2FA。如果攻击者能够访问letmein密钥,有两种情况:要么存在第二个安全屏障(例如ssh服务器登录),要么无论如何都会输,因为攻击者已经完全访问了。
-
弱点:所有能够成功认证letmein的用户都可以开始攻击受保护的服务。
- 原因:是的,这几乎是不可能防止的。letmein旨在防止预认证攻击。但是,可以限制用户访问某些端口。这样,用户只能使用服务器配置中明确允许的资源进行认证。
-
弱点:有线协议没有针对未来更改和更新的机制。
- 原因:虽然这会使更新到新协议版本变得困难,但它通过简化设计提高了安全性。预计未来不会有太多不兼容的协议更改。
许可
版权(c)2024 Michael Büsch [email protected]
根据您的选择,许可协议为Apache License版本2.0或MIT许可。
依赖
~10–19MB
~261K SLoC