密码学入门之密码
最近在研读《图解密码技术》这本书,将有一系列的密码学学习笔记,涉及到密码的相关概念、对称加密、非对称加密、单向散列函数、消息认证码、数字签名、数字证书等内容,同时涉及到代码部分也会使用Golang进行展示,感兴趣的可以关注更新哦。好了,今天先讲讲密码学中的一些概念性的问题。
发送者、接收者和窃听者
请想象一个Alice向Bob发送电子邮件的场景。在这个场景中,发出邮件的Alice称为 发送者(sender),而收到邮件的Bob则称为 接收者(receiver)。
当某个人向另一个人发送信息时,发出信息的人称为发送者,而收到信息的人称为接收者。另外,被发送的信息有时也统称为 消息(message)。
邮件是通过互联网从Alice的计算机发送到Bob的计算机的。在发送邮件时,邮件会经过许多台计算机和通信设备进行中转,在这个过程中,就存在被恶意窃听者(eavesdropper)偷看到的可能性
窃听者Eve并不一定是人类,有可能是安装在通信设备上的某种窃听器,也可能是安装在邮件软件和邮件服务器上的某些程序。
尽管邮件内容原本应该只有发送者和接收者两个人知道,但如果不采取相应的对策,就存在被第三方知道的风险。
加密和解密
那么如何防止窃听者的窃听呢?Alice不想让别人看到邮件的内容,于是她决定将邮件进行**加密(encrypt)**后再发送出去。
加密之前的消息称为明文(plaintext),加密之后的消息称为密文(cipher-text)。
- 明文加密之后就会变成看不懂的密文
Bob收到了来自Alice的加密邮件,但作为接收者的Bob也是无法直接阅读密文的,于是
Bob需要对密文进行解密(decrypt)之后再阅读。解密就是将密文恢复成明文的过程。
- 密文解密之后就变成了原来的明文
将消息加密后发送的话,即使消息被窃听,窃听者得到的也只是密文,而无法得知加密前的明文内容
-
将消息加密后发送, 窃听者只能得到密文
在上述场景中,Alice将邮件进行加密,而Bob则进行解密,这样做的目的,是为了不让窃听者Eve读取邮件的内容Alice和Bob通过运用密码(cryptography)技术,保证了邮件的机密性(confidentiality)。
秘钥
密码算法
用于解决复杂问题的步骤,通常称为算法(algorithm)。从明文生成密文的步骤,也就是加密的步骤,称为“加密算法",而解密的步骤则称为“解密算法"。加密、解密的算法合在一起统称为密码算法。
秘钥
密码算法中需要**(key)。现实世界中的“钥’’,是像 ???? 这样的形状微妙而复杂的小金属片。然而,密码算法中的**,则是像203554728568477650354673080689430768这样的一串非常大的数字。
加密、解密与秘钥
无论是在加密时还是在解密时,都需要知道**。
正如保险柜的钥匙可以保护保险柜中存放的贵重物品一样,密码中的**可以保护你的重要数据。即使保险箱再坚固,如果钥匙被盗, 里面的贵重物品也会被盗。同样地我们也必须注意不要让密码的**被他人窃取。
凯撒密码
恺撒密码(Caesar cipher)是一种相传尤利乌斯·恺撒曾使用过的密码。恺撒于公元前100年左右诞生于古罗马,是一位著名的军事统帅。
恺撤密码是通过将明文中所使用的字母表按照一定的字数“平移”来进行加密的。比如在日语(例如平假名)或者汉语(例如汉语拼音)或者英文字母表中都可以用同样的思路来实现恺撒密码。
为了讲解方便,我们用小写字母(a,b,c,…)来表小明文,用大写字母(A,B,C,…)来表示密文。
现在我们将字母表平移3个字母,于是,明文中的a在加密后就变成了与其相隔3个字母的D,以此类推。b变成E,c变成F,d变成G…v变成Y,w变成Z,而x则会回到字母表的开头而变成A,相应地,y变成B,z变成C。通过下图我们可以很容易地理解“平移"的具体工作方式。
凯撒密码的加密
这里,我们假设要保密的信息为monkey d luffy这个男孩的名字。我们暂且不管这个名字到底代表一位真实的男性,还是只是一种暗号,只考虑将它在保密的状态下发送给接收者。
此时,明文包含下列12个字母:monkeydluffy, 接下来我们对明文中的字母逐一加密:
m ---> P
o ---> R
n ---> Q
k ---> N
e ---> H
y ---> B
d ---> G
l ---> O
u ---> X
f ---> I
f ---> I
y ---> B
这样,明文 monkey d luffy 就被转换成了密文PRQNHB G OXIIB,monkey d luffy这个词我们能够看懂,但
PRQNHB G OXIIB就看不懂了。
恺撒密码中,将字母表中的字母平移这个操作就是密码的算法,而平移的字母数量则相当于**。在上面的例子中,**为3(如下图)。
凯撒密码的解密
现在,假设接收者已经收到了密文PRQNHB G OXIIB,由于密文本身是看不懂的,因此必须将它解密成明文。
恺撒密码的解密过程是使用与加密时相同的**进行反向的平移操作。用刚才的例子来说,只要反向平移3个字母就可以解密了。
P ---> m
R ---> o
Q ---> n
N ---> k
H ---> e
B ---> y
G ---> d
O ---> l
X ---> u
I ---> f
I ---> f
B ---> y
这样我们就得到了明文monkeydluffy。
在这个场景中, 秘钥3必须由发送者和接收者事先约定好。
密码信息安全常识与威胁
密码信息安全常识
在继续下面的内容之前,我们先来介绍一些关于密码的常识。刚刚开始学习密码的人常常会对以下这几条感到不可思议,因为它们有悖于我们的一般性常识。
- 不要使用保密的密码算法
- 使用低强度的密码比不进行任何加密更危险
- 任何密码总有一天都会被**
- 密码只是信息安全的一部分
不要使用保密的密码算法
很多企业都有下面这样的想法:
“由公司自己开发一种密码算法,并将这种算法保密,这样就能保证安全。然而,这样的想法却是大错特错,使用保密的密码算法是无法获得高安全性的。我们不应该制作或使用任何保密的密码算法,而是应该使用那些已经公开的、被公认为强度较高的密码算法。
这样做的原因主要有以下两点:
-
密码算法的秘密早晚会公诸于世
从历史上看,密码算法的秘密最终无一例外地都会被暴露出来。例如: RSA公司开发的RC4密码算法曾经也是保密的,但最终还是有一位匿名人士开发并公开了与其等效的程序。
一旦密码算法的详细信息被暴露,依靠对密码算法本身进行保密来确保机密性的密码系统也就土崩瓦解了。反之,那些公开的算法从一开始就没有设想过要保密,因此算法的暴露丝毫不会削弱它们的强度。
-
开发高强度的密码算法是非常困难的
- 要比较密码算法的强弱是极其困难的,因为密码算法的强度并不像数学那样可以进行严密的证明。密码算法的强度只能通过事实来证明,如果专业密码破译者经过数年的尝试仍然没有**某个密码算法,则说明这种算法的强度较高。
- 稍微聪明一点的程序员很容易就能够编写出“自己的密码系统"。这样的密码在外行看来貌似牢不可破,但在专业密码破译者的眼里,要**这样的密码几乎是手到擒来。
- 现在世界上公开的被认为强度较高的密码算法,几乎都是经过密码破译者长期尝试**未果而存活下来的。因此,如果认为“公司自己开发的密码系统比那些公开的密码系统更强”,那只能说是过于高估自己公司的能力了。
- 试图通过对密码算法本身进行保密来确保安全性的行为,一般称为隐蔽式安全性(securitybyobscurity),这种行为是危险且愚蠢的。
- 反过来说,将密码算法的详细信息以及程序源代码全部交给专业密码破译者,并且为其提供大量的明文和密文样本,如果在这样的情况下破译一段新的密文依然需要花上相当长的时间,就说明这是高强度的密码。
使用低强度的密码比不进行任何加密更危险
一般人们会认为.就算密码的强度再低,也比完全不加密要强吧?其实这样的想法是非常危险的。
**正确的想法应该是:**与其使用低强度的密码,还不如从一开始就不使用任何密码这主要是由于用户容易通过“密码”这个词获得一种“错误的安全感”。对于用户来说,安全感与密码的强度无关,而只是由“信息已经被加密了”这一事实产生的,而这通常会导致用户在处理一些机密信息的时候麻痹大意。
任何密码总有一天会被破译
如果某种密码产品宣称“本产品使用了绝对不会被**的密码算法”,那么你就要对这个产品的安全性打个问号了,这是因为绝对不会被**的密码是不存在的。
无论使用任何密码算法所生成的密文,只要将所有可能的**全部尝试一遍,就总有一天可以破译出来。因此,破译密文所需要花费的时间,与要保密的明文的价值之间的权衡就显得非常重要。
密码只是信息安全的一部分
我们还是回到Alice给Bob发送加密邮件的例子。即便不去**密码算法,也依然有很多方法能够知道Alice所发送的邮件内容, 例如:
攻击者可以不去试图破译经过加密的邮件,而是转而攻击Alice的电脑以获取加密之前的邮件明文。
上面提到的攻击手段,都与密码的强度毫无关系。要保证良好的安全性,就需要理解“系统”这一概念本身的性质复杂的系统就像一根由无数个环节相连组成的链条,如果用力拉,链条就会从其中最脆弱的环节处断开。因此,系统的强度取决于其中最脆弱的环节的强度。
最脆弱的环节并不是密码,而是人类自己。
密码信息威胁
我们将信息安全所面临的威胁与用来用对这些威胁的密码技术直接的关系用一张图标来表示出来。
欢迎与我交流