什么是对称加密
对称加密是一种加密算法,也称为私钥加密或共享密钥加密。在这种加密方式中,加密和解密使用的是同一个密钥。这意味着通信双方需要共同拥有一个密钥,用这个密钥对信息进行加密和解密。对称加密的主要优点是它的效率高,而且算法简单,易于实现。然而,密钥的管理和分发是一个重要的问题,因为一旦密钥丢失或被窃取,就可能导致信息的泄露。常见的对称加密算法包括AES、DES等。
其实,对称加密很早就存在于我们的社会实践中,如果有同学看过《潜伏》这部电视剧,一定对密码不会感到陌生:《潜伏》中余则成接受上级“农夫”指令的典型模式是用普通收音机收听广播,首先抄收一段数码,然后总是查看一本书,就翻译出上级指令。抄收的那些数码含义,也是事前约定。随便举个例子,比方9145这个数,它的含义按约定可能是第91页第4行的第5个字。余则成只要翻查那本约定的书,找到“第91页第4行的第5个字”,则这个字就翻译出来了。密钥就是那本书本身,要是对方掌握了是那本书,则就算破解了。
其中,加密解密较为简单,且密码本制作成本比较低,在电视剧中,密码本只是随便的一本小说:《蝴蝶梦》。当然,事务都有两面性,对称加密虽然简单好用,但是致命的缺点是,一旦密钥,即电视剧中的密码本被敌方截获,则通信中的所有密文全部会被破解。下面我们尝试用一段代码来实现AES对称加密:
public static void main(String[] args) {
//下面是会自动生成一段比特 用作加解密的密钥
AES aes = SecureUtil.aes();
byte[] bytes = aes.getSecretKey().getEncoded();
System.out.println("密钥为"+Arrays.toString(bytes));
//需要加密的马文
String message="周五早上9点发动";
String encryptBase64 = aes.encryptBase64(message);
System.out.println("密文为"+encryptBase64);
System.out.println("开始解密");
String decryptStr = SecureUtil.aes(bytes).decryptStr(encryptBase64);
System.out.println("解密出的密文为:"+decryptStr);
}
密钥为[-74, -61, -106, -54, -100, 4, 76, 27, -36, -85, 87, -36, -56, -123, 34, -70]
密文为mShCNVtcoaZCuBLHsdQfWWbTJMjCE+cldtIbZ8zYThg=
开始解密
解密出的密文为:周五早上9点偷袭敌方
我们发现,只需要使用和加密时相同的密钥,就能够破解出密文。但是在网络传输中,密钥是很容易被第三方截获的,因此,有没有什么办法,可以在密钥被截获的场景下,仍然能够防止第三方破解出密文呢?别急,接下来,就给大家介绍一个大招:非对称加密。
非对称加密
非对称加密,也称为公钥加密,是一种使用两个不同密钥进行加密和解密的加密方式。这两个密钥分别是公钥和私钥。公钥可以公开,任何人都可以使用它来加密信息,但只有私钥的持有者才能解密这些信息。这种加密方式的主要优点是它解决了密钥配送的问题,因为公钥可以公开分发,而私钥只需保密保存。非对称加密在保障通信安全方面发挥了重要作用,常见的非对称加密算法包括RSA、ElGamal等。
那么,我们该如何理解非对称加密呢?光看上面这段解释,有点过于“官方”了,下面我给大家举个通俗的例子:
假设屏幕前的你是一位兢兢业业的打工人,但是你发现,你的同事小明总监,正在偷偷的挪用公司的公共资源进行非法套现,给公司带来了巨大的损失,因此,你偷偷的把这个情况告诉了你的老板老雷,老雷通过财务审计,发现了小明的非法事迹,最后给予小明无偿解雇处理,你因此也受到了嘉奖,晋升为新的总监,但是,在你给老雷“打小报告”的过程中,被其他同事截获到了消息,大家都开始孤立你。你也很无奈,于是找到老雷诉说了自己心中的困惑,老雷也很头大,得想一个法子,怎样能够让员工打的小报告只有自己才知道里面的真实内容,并且只有自己才能够颁发新的人事任命通告,下面的职员也能够验证该通告的“真实性”呢?此时,你给老雷献上了一记:非对称加密。
具体是怎么操作呢?你建议老雷把自己的SFZ号码这一串数字作为“公钥”,然后公开暴露给所有的员工,以后所有的员工,如有需要给老雷打小报告,则只需要把老雷公开的SFZ号码当做公钥,对自己的小报告“加密”后,再转交给老雷。这样,即使中间人截取了你的“小报告”,但是仍然看不懂里面的真实内容,因此,也就实现了基层员工可以大胆的向老雷“检举揭发”了。可是,对于老雷来说,又该如何解开基层员工的密文呢?此时,你突然拍起脑袋,说到:“雷老板,与公钥配套的还有一另外一串数字,就是你的YHK密码,其实就是传说中的“私钥,这串私钥只有你自己一个人知道,可不能泄露出去了,你只需要用你的YH密码(私钥)来解密密文,就可以获得真实的小报告啦!”。雷老板惊呼到:“你可真是个小天才!秀!陈独秀!蒂花之秀!”。雷老板又推测到:“是不是意味着,我写的要开除小明的通告,也可以用私钥去加密(签名),将加密后的内容作为签名,这样,因为知道私钥(我YHK密码)的人只有我自己,基层员工就可以用我的SFZ号码(公钥)去验证签名内容是不是来自于我亲自签发的了!”你惊呼到:“不愧是老板,理解能力真强!”。
以下是基层员工向雷老板“打小报告” 的流程图。
以下是老板使用“私钥”加密(签名)人事任命通知。员工用“公钥”解密(验证签名)人事通知信息。
我们再来总结一下,你给老雷提出的解决方案:
建立公钥和私钥:老雷可以作为公司的唯一公钥和私钥的持有者。公钥可以公开给所有的员工,用于加密他们的小报告。而私钥则只有老雷一个人知道,用于解密这些报告。
报告提交:当员工发现同事的不当行为时,他们可以使用公钥加密他们的报告,然后提交给老雷。由于只有老雷持有私钥,因此只有他能够解密并阅读这些报告的内容。
验证和颁布:老雷在解密并验证了报告的真实性后,可以使用私钥加密一个新的人事任命通告,然后将其公之于众。所有员工都可以使用公钥来解密这个通告,并验证它的真实性,因为只有老雷的私钥能够加密这个通告。
这种方法确保了只有老雷一个人能够知道打小报告的内容,同时又能让所有员工验证人事任命通告的真实性。这既保护了打小报告员工的隐私,又维护了公司的公正和透明。但是在上面这个描述中仅仅是为了方便初学者理解,用SFZ号码作为公钥,YHK密码作为私钥的概念并不准确。在真实的非对称加密系统中,公钥和私钥是数学上相关的一对密钥,不是简单的SFZ号码和YHK密码。而且,非对称加密涉及到复杂的数学运算,通常需要使用专门的加密库或工具来实现。实际上,非对称加密中的私钥应该是一个随机生成的、足够长的数字,并且需要妥善保管。
下面我们使用非对称加密算法中的RSA算法来实操一下:
public static void main(String[] args) {
RSA rsa = SecureUtil.rsa();
String publicKeyBase64 = rsa.getPublicKeyBase64();
String privateKeyBase64 = rsa.getPrivateKeyBase64();
System.out.println("生成的公钥:"+publicKeyBase64);
System.out.println("生成的私钥"+privateKeyBase64);
//模拟员工向老板打小报告的过程
String reportText="雷老板,小明经理私自挪用公司资源套现,请明察!";
//模拟员工使用公钥来加密小报告
String encryptBase64 = rsa.encryptBase64(reportText, KeyType.PublicKey);
System.out.println("小报告加密后的内容:"+encryptBase64);
//模拟老板使用私钥解密小报告
byte[] decryptBase64 = rsa.decrypt(encryptBase64, KeyType.PrivateKey);
System.out.println("老板解密后的小报告内容:"+ new String(decryptBase64));
//老板新的任命通告
String assignText="此即日起,任命屏幕前的你为新的经理!";
//模拟老板对通告内容签名,内容可能很长,所以一般不直接加密(签名)原文,而是加密原文的哈希值,此处使用MD5
byte[] md5Hash = DigestUtil.md5(assignText);
System.out.println("原文的Hash值为:"+new String(md5Hash));
String hashAssign = rsa.encryptBase64(md5Hash, KeyType.PrivateKey);
System.out.println("老板对人事任命内容的签名值为:"+hashAssign);
//模拟员工对老板的人事通知解密(验签)过程
System.out.println("员工使用老板公钥解密的签名为:"+new String(rsa.decrypt(hashAssign,KeyType.PublicKey)));
}
生成的公钥:MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCqpCssglgz6ferj5RUmZO2hxrT7yBjrXH45LC70QxfOWPRyPZ35U3TQ6hLPqSpMoWUcLHstsxVC60uvyjeKuripgZvlkd53NZhMCFdJTTtcmB8saiP2viwr829AP/nz3zeprxAv1WDsT8+XtQvVnrf6yWp4l28vzu890/ESc/8VwIDAQAB
生成的私钥MIICeAIBADANBgkqhkiG9w0BAQEFAASCAmIwggJeAgEAAoGBAKqkKyyCWDPp96uPlFSZk7aHGtPvIGOtcfjksLvRDF85Y9HI9nflTdNDqEs+pKkyhZRwsey2zFULrS6/KN4q6uKmBm+WR3nc1mEwIV0lNO1yYHyxqI/a+LCvzb0A/+fPfN6mvEC/VYOxPz5e1C9Wet/rJaniXby/O7z3T8RJz/xXAgMBAAECgYAqBOcEvMwPbIuqWV7DPlYbWkWG7plhMjKggV/rv9x2DmHAJOZcO8DgRwbIEJLnfyNZnC6UBadnQcrReg0MODFCWXaWlC+OTxa/BjBP/ZAt1eAdLE/8hSk13nrvSTPft/12aZNrok4w/wk0h8S+dKeej1Ixb0kjyWVnM9yrjpdDEQJBAP8kFWuF482aJQg59t4FjWLocmh3xzC/uXUwNpHUT/BWJoc0Wcqy7/FGMwdK29HQxK/xwiNqVBsqZiYA5JTaswsCQQCrN0BUWOm+UPtzdHO7ZWIO7iwpsxo/NrqCdnlEAQiY/EtxpC7R9f8wBvKEN/nuuXlxkd3jJDf20quJ5OKjLatlAkEAo7k9AZWWfE5JK0E++HQpqWmuWPlb2h193gSFUAklDv3JlYNzh05SCMraXficnMRSIvGJef52YERR7lsuU5MPxwJBAJL3b0m3tJR/sQeuuzTtVpmYSeJVcb83PCuGhJsiA/5F+oCGvQXPEghovj1OS0Rmgt9ApWU3Dq7YsRRBm2UUa50CQQCL3pZeDXGdwBai9Xbz9tDAeU8yw5yZWw/HGCYZTy7aBdHQ5O55XrkbArATIXajTJtlKs3DMB+lddm2QR6oULnL
小报告加密后的内容:l80m9nGdRO9WHPqJwRh4FFcL27yIa2NuEEYbwNZs50VitTtvR8dNmYcAnpQ5HoBNqVh0glMWhr3CiCjxT93We33eWgJlQAtFqBrfqKP/bLmniaDCPSxwow9Kk+e5buCQWjf7iF/f/LglJVOLr6LXVzSzsWtvbbPt3EmvCcLwUU4=
老板解密后的小报告内容:雷老板,小明经理私自挪用公司资源套现,请明察!
原文的Hash值为:<�M�z{9`���
老板对人事任命内容的签名值为:UONNwOcrd7cvXlmgfXdl5Lq9ISV6u26yo9tygtDb31AxLrbAMzVfRP2swR1zJ00+0FUyF+szIrYpG2jmn0ACYcp44BC+D/WWl0RHRwa87R3Y+0AC9us8QAlJhJQdA/q92so4JIBbYedb5uCWzwK81sfHYYDv3jPbDRB8Gvs6Yko=
员工使用老板公钥解密的签名为:<�M�z{9`���
我们发现,员工使用老板的公钥解密后得到的原文Hash值与通告上老板声明的Hash只一致,表明该通告不仅没有遭受篡改,并且确实是老板本人亲自发出的。因此,这样就解决了前面开始“对称加密”遗留的问题:密钥分发过程中泄露导致被破译。而如今,公钥可以任意分发给任何人,私钥只有自己知道,这样即使公钥在分发过程中被泄露,也并不会带来什么影响。因为加密,解密用的并不是同一套密钥,而且值得注意的一点是:非堆成加密还多带来了“签名”的特性,我们再来总结一下非对称加密的签名方面的特点:
签名是指使用私钥对原始数据进行加密,生成一个独特的数字签名,用于验证数据的来源和完整性。签名可以保证数据没有被篡改或伪造。
验签是指使用公钥对数字签名进行解密,并将解密后的数据与原始数据进行比较,以验证数据的来源和完整性。如果解密后的数据与原始数据一致,则说明数据没有被篡改或伪造。
如果你很好的理解了非对称加密的加解密以及签名验签,那么对于“证书”的理解,就会非常的顺利啦!
数字证书
老雷经过使用你提出的非对称加密算法方案来保护公司打小报告员工的隐私问题,公司的业绩不仅开始蒸蒸日上,而且偷偷私自挪用公款的现象得到了遏制。然而,好景不长,公司出现了一些奇怪的现象。部分同事的小报告内容竟然被一一破解了,并且大肆的在公司的内网上面流传,而且,出现了一些难以理解的人事任命通知:其中竟然有一封通告竟然把保洁大爷老刘任命为公司新老板,并且通过老雷的“公钥”验证是真实可信的!老雷作为公司的真老板,感到非常的愤怒和疑惑。他立即拉来你,向你说明了情况,要求你在7个工作日内探明案情!你也感到百思不得其解,于是,卧底在部门群内,逐一了解大家是怎么对小报告加密,怎么对通告验签的。突然,有人反映到,在上个星期,有个匿名员工在公告群里发了一封通告,说雷老板的SFZ掉了,换了新的SFZ。SFZ号码(对应公钥)也换了,大家按照新的SFZ信息(公钥)来加密小报告和验证人事通知。你感觉到事情有些蹊跷,你是雷老板最信得过的员工,雷老板以前掉了SFZ都会直接找你帮他代办理,可是这次为什么没有通知你呢?你跑到雷老板办公室抛出了你的疑问,雷老板震惊到:“我没掉SFZ啊,我也没换新呢!以前SFZ(公钥)好好用着呢!”,你恍然大悟,立即去论坛上找到那篇通告里的“新SFZ”,果然,这张“新SFZ”是用PS伪造的!信息还是雷老板的信息,但是对应的SFZ号码(公钥)却变成了另外一串数字!你恍然大悟道,原来有小人从中作梗!伪造了雷老板的SFZ,导致大家用“假”的公钥加密小报告,最后小报告也只有小人手中有正确的私钥,他才能一一解密小报告的内容,并在内网上传播。并且,那些乱七八糟的新人事任命通告,也是这个小人用自己的私钥签名的,然后大家又误用了新的SFZ号码(公钥)去验证,恰好能够验证通过。你终于找到了核心问题所在:即SFZ是可以造假的!任何人都可以任意篡改老雷的真实SFZ号码并发布出去。大家压根辨别不出老雷的真实SFZ号码(密钥)是多少!
你回到家,彻夜难眠,该如何解决这个问题呢?你躺在床上,想出这种情况下,问题的根源在于公钥(SFZ号码)的验证机制没有被正确实施,以及对于公钥的更改没有建立一个安全、可靠的通知和确认机制。
因此,你想出了下面这个方法:
- 引入一个可信赖的第三方机构来管理和验证(SFZ)公钥。
- 每个人或者部门的(SFZ)公钥都会被第三方机构签名认证,形成一个数字证书。
- 当需要验证(SFZ证)公钥的真实性时,可以通过检查数字证书来确认。
因此,你向全国RD代表提出,所有的SFZ都必须经过上一级部门使用其自己对应的私钥来对证书内容“签名”,这样公众就可以用上级的公钥(SFZ号码)对它颁发的下级SFZ进行验签。来判断是不是真实上级签发的。例如,老雷的SFZ号码为4430563412123456,他的SFZ颁发机构(上级)为深圳市GAJ,上级对老雷SFZ信息的签名值为:l80m9nGdRO9WHPqJw。此时,如果你需要验证一张有关老雷的SFZ是不是真的,即老雷对应的SFZ号码是不是所谓的4430563412123456这一串数字。则你只需要使用深圳市GAJ的SFZ号码(假设存在)去验证老雷的SFZ信息是否正确。如果能够验签成功,则证明这张老雷的SFZ号码确实是真的,他对应的SFZ号码确实是这串数字,则员工们可以大胆用这串数字当做公钥来加密小报告信息和验证新的人事通告。
正当你为自己的解决方案洋洋得意的时候,员工丽丽突然问到:你这方案挺好的,既然不确定有关雷老板的SFZ是否真实,那就用上级签发机关对应的公钥来验签,如果验签成功,则能保证该信息是经过真实上级签发的对吧?那么问题来了,雷老板的上级:深圳市GAJ的SFZ号码难道就一定是真的吗?GAJ的SFZ和老雷的没有什么差别,只是所处的层级结构不同,GAJ是老雷的上级,是给老雷颁发SFZ以及做签名的机构。但是,你又如何保证GAJ的SFZ信息是真实的呢?也就是说,倘若小人现在不伪造老雷的SFZ信息了,改成直接伪造深圳市GAJ的SFZ信息,那危害范围更加大了,就不仅仅是只造假老雷一份人的SFZ信息了,而是可以任意伪造任何的公民信息!这简直不敢想象!
你顿时陷入一顿抓狂中,当初为了保障老雷的SFZ信息的真实性,从而引入了它的上级:深圳市GAJ将对老雷的SFZ信息做签名担保。可是,深圳市GAJ的SFZ信息又有谁给他做签名担保呢?是广东省GAJ吗?可是广东省GAJ的SFZ信息又谁给他做签名担保呢?是GWY吗?那GWY呢?...从此陷入了一个“鸡生蛋,蛋生鸡”的无限递归问题:所有的上级链都不一定可信。
虽然问题比较棘手,但是你还是想到了解决方案:既然SFZ一直无限依赖上级,则我们只需要保证信任链最顶层的root 是大家公认的,是打小出生大家就认同的,则root的SFZ信息不需要上级来为他做担保签名,则保证了root一定是可信的,进而root往下颁发的所有SFZ都是可信的。因此,你在代表大会上,提议把GWY作为这个信任链最顶层的机构,即GWY的SFZ信息不需要其他人为他做签名担保,因为RM代表大会已经把GWY的SFZ号码(1000000000)写入了XF,并且要求从幼儿园开始熟读背诵,因此GWY(信任链顶级root)对应的SFZ号码(公钥)是不需要任何怀疑的。这样,就保证了信任链的最顶层是一定可信的,则所有人的SFZ号码都可以从GWY这一层一级一级往下验证下去,这样,一个授信链条就构建完成了。从此,公司的事业蒸蒸日上,你也被提拔成为公司的副经理,过上了幸福美满的生活。
将GWY作为信任链的最顶层,即GWY的SFZ信息不需要其他人为他做签名担保。因为RM代表大会已经将GWY的SFZ号码(1000000000)写入XF,并要求从幼儿园开始熟读背诵,因此GWY对应的SFZ号码(公钥)是不需要怀疑的。这样,可以保证信任链的最顶层是可信的,然后所有人的SFZ号码可以从GWY这一层一级一级往下验证,从而构建一个完整的授信链条。
这个方案是合理的,因为它确保了信任链最顶层的根是可信的,从而保证了整个信任链的有效性。通过这种方式,可以追溯和验证每个人的SFZ号码(公钥),确保其真实性和合法性。因此,这个方案具有可行性,可以为解决SFZ依赖上级的问题提供有效的解决方案。
注意:以上故事纯属虚构,请勿相信哈哈!
怎么样?是不是脑海里又想起了老雷的故事?其实现实世界的证书就类似于故事中的SFZ信息。而顶级的GWY就等同意网络世界中的顶级证书,GWY信息是深入人心。而现实世界顶级证书则是内置于现在的浏览器中,即我们可以简单认为顶级证书是一定可信的,这也就是为什么浏览器有的时候会提示你禁止随意信任根证书的原因了,因为这样相当于从根源改变了整个信任链体系。当然,虽然CA证书方便了层层授权,但是也带了一定的缺陷:即所有的证书源头是CA机构,如果你想生成自己的证书,则必须要找根证书机构去做签名,此时根证书机构可以向你提出收费,如果你不舍的出钱,则你就拿不到CA给你颁发的证书,你的网站就会被全世界的浏览器提示为不安全网站,这就带有一点点垄断的味道了。当然,也有些网站就是不低头,比如我们以前的12306,就是自己作为顶级给自己颁发证书,因此以前12306登录的时候会提醒你下载安装并信任他的根证书。当然现在的12306已经有了正式的证书了。
顶级CA机构有GeoTrust、Comodo、Symantec、RapidSSL等。
中国铁路总公司下属的12306购票网站在2011年正式上线,自上线以来就使用自签名SSL证书对访问流量进行加密,这种操作的弊端就是用户在访问12306官网进行购买的时候,需要提前下载自签名SSL证书并安装到自己的设备中,否则浏览器会在加载的时候直接进行拦截,严重影响交易量。
现在来看12306网站的话,是已经安装了EV SSL证书。EV SSL证书是目前安全等级最高的证书,可以在网址前直接显示出企业的名称。
最后为了便于学习,我们把数字证书抽象成最简单的模型,即只包含:个人信息,公钥,签名,签发上级这4个字段。那么,数字证书可以很简单的总结为:
参考资料
-
《潜伏》中的“密码”通讯 《潜伏》中的“密码”通讯_网易新闻
-
知乎-安信证书 为什么 12306 不买 https 证书? - 知乎
基础不牢?新手不友好?无人带路?关注《扬俊的小屋》公众号吧!
博客文章版权说明
第一条 本博客文章仅代表作者本人的观点,不保证文章等内容的有效性。
第二条 本博客部分内容转载于合作站点或摘录于部分书籍,但都会注明作/译者和原出处。如有不妥之处,敬请指出。
第三条 在征得本博客作者同意的情况下,本博客的作品允许非盈利性引用,并请注明出处:“作者:____转载自____”字样,以尊重作者的劳动成果。版权归原作/译者所有。未经允许,严禁转载。
第四条 对非法转载者,“扬俊的小屋”和作/译者保留采用法律手段追究的权利。
第五条 本博客之声明以及其修改权、更新权及最终解释权均属“扬俊的小屋”。
第六条 以上声明的解释权归“扬俊的小屋”所有。