在网络应用程序中处理数字签名
Handling digital signature in network applications
TL;DR
我是否必须在每条消息上签名,或者是否有更有效的方法来验证消息的来源?
为了好玩,我正在开发一个简单的加密协议。当然我知道在任何严肃的项目中,我应该只使用一些行业标准,比如 OpenSSL,但这是为了学习和试验。
想法是通信终端交换 RSA public 密钥,然后使用这些密钥安全地交换 AES 密钥,这样 AES 密钥就可以用来加密从这一点开始的每条消息。我已经实现了所有这些,并且运行良好。
问题是:由于 AES,潜在的攻击者无法读取任何内容,但仍然可能导致错误或试图劫持通信或通过中间人(例如she/he 可以复制加密的消息并通过一次又一次地发送来破坏事物)。我需要的是数字签名,这样我就可以确认消息来自有效来源,我很幸运,因为我已经有了一个有效的 RSA 实现。
我知道数字签名是如何工作的(获取消息的哈希值并使用私钥对其进行加密等),但我能想到的使这项工作有效的唯一方法是 签署每个single message,然后在接收端检查签名是否有效。但是,我担心这会 减慢 我的协议。使用 AES 来保护通信(或任何对称密钥加密)的全部目的是它比 RSA(或任何 public 密钥加密)快得多。这样做 不会破坏 AES(或任何对称密钥加密)的目的吗?所以问题是:我是否必须对每条消息都签名? 或者是否有更有效的方法?例如 OpenSSL 如何处理这个问题?
TL;DR 使用authenticated encryption.
在对称加密中,可以生成一个消息验证码 (MAC),使您能够检查您发送的消息是否被(恶意)操纵。 man-in-the-middle 攻击者为您未标记的消息伪造身份验证标记的优势微乎其微。
有很多方法可以做到这一点,但通常认为 MAC 应该验证密文而不是明文 (Should we MAC-then-encrypt or encrypt-then-MAC?)。流行的 MAC 算法是 HMAC(例如 HMAC-SHA256)、CMAC/OMAC1 或 GMAC。还有一些不同的身份验证模式,例如 GCM、EAX、OCB、SIV、CWC 等。它们结合了一种模式来实现机密性和真实性模式,而无需为两者使用不同的密钥。
但这还不够,因为这只能使接收方检测到消息的篡改或伪造。攻击者仍可能发起其他攻击,例如重放或延迟攻击。因此,您需要一起发送随机数(例如消息计数器)和时间戳。接收方必须保留先前发送的消息的记录(通过存储随机数),并且不接受任何根据其内部时钟判断发送得太晚的消息。
为了防止攻击者随意更改随机数和时间戳,这些也必须经过身份验证。大多数经过身份验证的模式实际上是 带有关联数据的经过身份验证的加密,它可以验证额外的 non-secret 数据,例如随机数和时间戳。
使用经过身份验证的加密可以使相对 tamper-proof 的纯对称通信假设密钥是秘密交换的,并且还通过常规 digital-signatures 验证,例如 RSA-PSS 或Ed25519 (EdDSA).
TL;DR
我是否必须在每条消息上签名,或者是否有更有效的方法来验证消息的来源?
为了好玩,我正在开发一个简单的加密协议。当然我知道在任何严肃的项目中,我应该只使用一些行业标准,比如 OpenSSL,但这是为了学习和试验。
想法是通信终端交换 RSA public 密钥,然后使用这些密钥安全地交换 AES 密钥,这样 AES 密钥就可以用来加密从这一点开始的每条消息。我已经实现了所有这些,并且运行良好。
问题是:由于 AES,潜在的攻击者无法读取任何内容,但仍然可能导致错误或试图劫持通信或通过中间人(例如she/he 可以复制加密的消息并通过一次又一次地发送来破坏事物)。我需要的是数字签名,这样我就可以确认消息来自有效来源,我很幸运,因为我已经有了一个有效的 RSA 实现。
我知道数字签名是如何工作的(获取消息的哈希值并使用私钥对其进行加密等),但我能想到的使这项工作有效的唯一方法是 签署每个single message,然后在接收端检查签名是否有效。但是,我担心这会 减慢 我的协议。使用 AES 来保护通信(或任何对称密钥加密)的全部目的是它比 RSA(或任何 public 密钥加密)快得多。这样做 不会破坏 AES(或任何对称密钥加密)的目的吗?所以问题是:我是否必须对每条消息都签名? 或者是否有更有效的方法?例如 OpenSSL 如何处理这个问题?
TL;DR 使用authenticated encryption.
在对称加密中,可以生成一个消息验证码 (MAC),使您能够检查您发送的消息是否被(恶意)操纵。 man-in-the-middle 攻击者为您未标记的消息伪造身份验证标记的优势微乎其微。
有很多方法可以做到这一点,但通常认为 MAC 应该验证密文而不是明文 (Should we MAC-then-encrypt or encrypt-then-MAC?)。流行的 MAC 算法是 HMAC(例如 HMAC-SHA256)、CMAC/OMAC1 或 GMAC。还有一些不同的身份验证模式,例如 GCM、EAX、OCB、SIV、CWC 等。它们结合了一种模式来实现机密性和真实性模式,而无需为两者使用不同的密钥。
但这还不够,因为这只能使接收方检测到消息的篡改或伪造。攻击者仍可能发起其他攻击,例如重放或延迟攻击。因此,您需要一起发送随机数(例如消息计数器)和时间戳。接收方必须保留先前发送的消息的记录(通过存储随机数),并且不接受任何根据其内部时钟判断发送得太晚的消息。
为了防止攻击者随意更改随机数和时间戳,这些也必须经过身份验证。大多数经过身份验证的模式实际上是 带有关联数据的经过身份验证的加密,它可以验证额外的 non-secret 数据,例如随机数和时间戳。
使用经过身份验证的加密可以使相对 tamper-proof 的纯对称通信假设密钥是秘密交换的,并且还通过常规 digital-signatures 验证,例如 RSA-PSS 或Ed25519 (EdDSA).