数字签名的方法分为直接对消息签名的方法和对消息的散列值签名的方法;下面我们来具体介绍两种生成和验证数字签名的方法。
直接对消息签名的方法比较容易理解,但实际上并不会使用;对消息的散列值签名的方法稍微复杂一点,但实际中我们一般都使用这种方法。
直接对消息签名的方法
发送者 A要对消息签名,而接收者B要对签名进行验证,我们来讲一下具体的方法。
A需要事先生成一个包括公钥和私钥的密钥对,而需要验证签名的B则需要得到A的公钥。在此基础上,签名和验证的过程如下:
(1)A用自己的私钥对消息进行加密。
用私钥加密得到的密文就是A对这条消息的签名,由于只有 A才持有自己的私钥,因此除了 A以外,其他人是无法生成相同的签名(密文)的。
(2)A将消息和签名发送给B。
(3)B用A的公钥对收到的签名进行解密。
如果收到的签名确实是A的私钥进行加密得到的密文(签名),那么用 A的公钥应该能够正确解密。如果收到的签名不是用 A的私钥进行加密得到的密文,那么就无法用 A的公钥正确解密(解密后得到的数据看起来是随机的)。
(4)B将签名解密后得到的消息与A直接发送的消息进行对比。
如果两者一致,则签名验证成功;如果两者不一致,则签名验证失败。
对消息的散列值签名的方法
我们不必再对整个消息进行加密(即对消息签名),而是只要先用单向散列函数求出消息的散列值,然后再将散列值进行加密(对散列值签名)就可以了。无论消息有多长,散列值永远都是这么短,因此对其进行加密(签名)是非常轻松的。
(1)A用单向散列函数计算消息的散列值
(2) A用自己的私钥对散列值进行加密。
用私钥加密散列值所得到的密文就是 A对这条散列值的签名,由于只有 A才持
有自已的私钥,因此除了 A以外,其他人是无法生成相同的签名(密文)的。
(3)A将消息和签名发送给B。
(4)B用A的公钥对收到的签名进行解密。
如果收到的签名确实是用A的私钥进行加密而得到的密文(签名),那么用 A的公钥应该能够正确解密,解密的结果应该等于消息的散列值。如果收到的签名不是用A的私钥进行加密而得到的密文,那么就无法用 A的公钥正确解密(解密后得到的数据看起来是随机的)。
(5)B将签名解密后得到的散列值与 A直接发送的消息的散列值进行对比。如果两者一致,则签名验证成功;如果两者不一致,则签名验证失败。