2个版本
0.5.1 | 2019年6月12日 |
---|---|
0.5.0 | 2019年6月12日 |
#891 in 密码学
120KB
2K SLoC
Ossuary (libossuary)
Ossuary是一个库,用于在客户端和服务器之间建立一个加密和验证的通信通道。
它建立了一个1对1的客户端/服务器通信通道,该通道需要可靠的有序数据包交付,如TCP套接字所提供的那样。
远程主机的身份验证和验证是可选的,需要主机公钥的离线交换或首次使用即信任策略。
它是用Rust编写的,带有C FFI。它构建为一个Rust库,一个C动态库(libossuary.so/.dylib)和一个C静态库(libossuary.a)。
目的
Ossuary与TLS(或SSL)具有相同的目的:两个主机相互之间建立一个端到端的加密通信通道,在需要访问控制的情况下,可以选择在此过程中进行自我标识。
它主要区别在于简单性。它很小,简单且具有见解。它足够快,而且不会更快。
Ossuary只有一个用例:“我有一个TCP套接字,我想安全地通过它进行通信,并且我不想处理TLS。” 合理的使用场景包括命令和控制服务、日志记录、状态或传感器报告以及一次性文件传输。
它没有针对大量同时连接、频繁连接或快速重新建立连接进行特别优化。对于这些事情,你考虑过TLS吗?
方法
Ossuary被设计为一个用于加密和解密数据缓冲区的工具库。加密格式包含各种元数据,但所有这些对用户都是透明的。
Ossuary根本不涉及网络连接。父应用程序负责建立通信通道,无论是TCP、UDP、UNIX域套接字、D-Bus、RS-232还是烟雾信号。Ossuary在网络调用之间作为一个过滤器存在。在伪代码中,它可能看起来像这样
<Setup TCP socket and Ossuary>
while socket.connected():
// Read encrypted data from the network layer
data_from_network = socket.read();
// Decrypt the data with Ossuary
plaintext_data = ossuary.recv_data(data_from_network);
// React to the received message and get a plaintext response
response = application_parse_command(plaintext_data);
// Encrypt the response with Ossuary
data_to_network = ossuary.send_data(response);
// Write encrypted data to the network layer
socket.write(data_to_network);
<tear down TCP socket and Ossuary>
这种设计接受数据频繁复制的权衡,以牺牲最大带宽来换取简单的集成。
然而,当从Rust使用Ossuary时,你可以传递任何实现了Read和Write特质的对象。这意味着,为了方便起见,你可以直接传递TcpStream对象。这不会对性能有很大帮助,但它减少了简单集成所需的代码量。
Ossuary也不涉及持久存储。密钥的存储留给调用应用程序处理。
理由
野外可用的“安全通道”库非常少。TLS是最大的玩家,有数十种实现(OpenSSL、GnuTLS、LibreSSL、BoringSSL、mbed TLS、MatrixSSL、wolfSSL、s2n...)。libssh2也可以类似地使用,但这样做可能并不常见。另一个选择是跳过TCP层,使用像ZeroMQ这样的“分布式消息”系统,它具有CurveZMQ协议。
尽管实现之间的尺寸差异很大,并且定制最小构建是可行的,但桌面系统上默认构建的大小介于“大”和“巨大”之间。API的复杂性介于“中等”和“荒谬”之间。自我伤害的可能性介于“可能”和“绝对确定”之间。
Ossuary很小,但由于Rust,它不是微不足道的。Ossuary的API是最小和简单的。配置几乎为零。代码越少,安全性越高;代码越多,安全性就越低。
安全性
应假定:没有。不要假设来自互联网上随机人的不成熟的加密库是安全的。
API文档
版本
这是一个实验性的1.0预发布版。版本号没有任何意义,API是不稳定的。
依赖
底层加密原语来自第三方
底层随机数来自第三方
依赖
~3MB
~57K SLoC