密码学中的“盐值 Salt”

盐(Salt)

在密码学中,是指通过在密码任意固定位置插入特定的字符串,让散列后的结果和使用原始密码的散列结果不相符,这种过程称之为“加盐”。

以上这句话是维基百科上对于 Salt 的定义,但是仅凭这句话还是很难理解什么叫 Salt,以及它究竟起到什么作用。

第一代密码

早期的软件系统或者互联网应用,数据库中设计用户表的时候,大致是这样的结构:

mysql> desc User;
+----------+--------------+------+-----+---------+-------+
| Field    | Type         | Null | Key | Default | Extra |
+----------+--------------+------+-----+---------+-------+
| UserName | varchar(50)  | NO   |     |         |       |
| PassWord | varchar(150) | NO   |     |         |       |
+----------+--------------+------+-----+---------+-------+

数据存储形式如下:

mysql> select * from User;
+----------+----------+
| UserName | PassWord |
+----------+----------+
| lichao   | 123      |
| akasuna  | 456      |
+----------+----------+

主要的关键字段就是这么两个,一个是登陆时的用户名,对应的一个密码,而且那个时候的用户名是明文存储的,如果你登陆时用户名是 123,那么数据库里存的就是 123。这种设计思路非常简单,但是缺陷也非常明显,数据库一旦泄露,那么所有用户名和密码都会泄露,后果非常严重。参见《CSDN 详解 600 万用户密码泄露始末》。

第二代密码

为了规避第一代密码设计的缺陷,聪明的人在数据库中不在存储明文密码,转而存储加密后的密码,典型的加密算法是 MD5 和 SHA1,其数据表大致是这样设计的:

mysql> desc User;
+----------+--------------+------+-----+---------+-------+
| Field    | Type         | Null | Key | Default | Extra |
+----------+--------------+------+-----+---------+-------+
| UserName | varchar(50)  | NO   |     |         |       |
| PwdHash  | char(32)     | NO   |     |         |       |
+----------+--------------+------+-----+---------+-------+

数据存储形式如下:

mysql> select * from User;
+----------+----------------------------------+
| UserName | PwdHash                          |
+----------+----------------------------------+
| lichao   | 202cb962ac59075b964b07152d234b70 |
| akasuna  | 250cf8b51c773f3f8dc8b4be867a9a02 |
+----------+----------------------------------+

假如你设置的密码是 123,那么数据库中存储的就是 202cb962ac59075b964b07152d234b70 或 40bd001563085fc35165329ea1ff5c5ecbdbbeef。当用户登陆的时候,会把用户输入的密码执行 MD5(或者 SHA1)后再和数据库就行对比,判断用户身份是否合法,这种加密算法称为散列

严格地说,这种算法不能算是加密,因为理论上来说,它不能被解密。所以即使数据库丢失了,但是由于数据库里的密码都是密文,根本无法判断用户的原始密码,所以后果也不算太严重。

第三代密码

本来第二代密码设计方法已经很不错了,只要你密码设置得稍微复杂一点,就几乎没有被破解的可能性。但是如果你的密码设置得不够复杂,被破解出来的可能性还是比较大的。

好事者收集常用的密码,然后对他们执行 MD5 或者 SHA1,然后做成一个数据量非常庞大的数据字典,然后对泄露的数据库中的密码就行对比,如果你的原始密码很不幸的被包含在这个数据字典中,那么花不了多长时间就能把你的原始密码匹配出来。这个数据字典很容易收集,CSDN 泄露的那 600w 个密码,就是很好的原始素材。

于是,第三代密码设计方法诞生,用户表中多了一个字段:

mysql> desc User;
+----------+-------------+------+-----+---------+-------+
| Field    | Type        | Null | Key | Default | Extra |
+----------+-------------+------+-----+---------+-------+
| UserName | varchar(50) | NO   |     |         |       |
| Salt     | char(50)    | NO   |     |         |       |
| PwdHash  | char(32)    | NO   |     |         |       |
+----------+-------------+------+-----+---------+-------+

数据存储形式如下:

mysql> select * from User;
+----------+----------------------------+----------------------------------+
| UserName | Salt                       | PwdHash                          |
+----------+----------------------------+----------------------------------+
| lichao   | 1ck12b13k1jmjxrg1h0129h2lj | 6c22ef52be70e11b6f3bcf0f672c96ce |
| akasuna  | 1h029kh2lj11jmjxrg13k1c12b | 7128f587d88d6686974d6ef57c193628 |
+----------+----------------------------+----------------------------------+

Salt 可以是任意字母、数字、或是字母或数字的组合,但必须是随机产生的,每个用户的 Salt 都不一样,用户注册的时候,数据库中存入的不是明文密码,也不是简单的对明文密码进行散列,而是 MD5( 明文密码 + Salt),也就是说:

MD5('123' + '1ck12b13k1jmjxrg1h0129h2lj') = '6c22ef52be70e11b6f3bcf0f672c96ce'
MD5('456' + '1h029kh2lj11jmjxrg13k1c12b') = '7128f587d88d6686974d6ef57c193628'

当用户登陆的时候,同样用这种算法就行验证。

由于加了 Salt,即便数据库泄露了,但是由于密码都是加了 Salt 之后的散列,坏人们的数据字典已经无法直接匹配,明文密码被破解出来的概率也大大降低。

是不是加了 Salt 之后就绝对安全了呢?淡然没有!坏人们还是可以他们数据字典中的密码,加上我们泄露数据库中的 Salt,然后散列,然后再匹配。但是由于我们的 Salt 是随机产生的,假如我们的用户数据表中有 30w 条数据,数据字典中有 600w 条数据,坏人们如果想要完全覆盖的坏,他们加上 Salt 后再散列的数据字典数据量就应该是 300000* 6000000 = 1800000000000,一万八千亿啊,干坏事的成本太高了吧。但是如果只是想破解某个用户的密码的话,只需为这 600w 条数据加上 Salt,然后散列匹配。可见 Salt 虽然大大提高了安全系数,但也并非绝对安全。

实际项目中,Salt 不一定要加在最前面或最后面,也可以插在中间嘛,也可以分开插入,也可以倒序,程序设计时可以灵活调整,都可以使破解的难度指数级增长。

PS,文中所谓第一、二、三代密码的称呼,是我自己 YY 的。

From:http://www.libuchao.com/2013/07/05/password-salt

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/432770.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

android 主线程调用,Android 主线程和线程之间相互发送消息

通过分析Activity源码,我们知道每个Activity都有一个Looper,所以主线程在接收Message是不需要调用Looper.prepare()和Looper.loop(),但是线程是不带Looper的,当线程要接收来自主线程的消息是就需要调用Looper.prepare()和Looper.l…

10 个十分难得的 javascript 开发经验

Javascript 的很多扩展的特性是的它变得更加的犀利, 同时也给予程序员机会创建更漂亮并且更让用户喜欢的网站。 尽管很多的开发人员都乐于颂扬 javascript,但是仍旧有人看到它的阴暗面。 使用很多 javascript 代码的 web 页面会加载很慢,过多…

简单的UTF8编码生成

用记事本建一个文件,用editplus打开,并转成UTF8格式 然后写中文字符 然后用ultraEdit打开,切换到16机制模式即可

android unzip file,Unzip File in Android Assets

可以将文章内容翻译成中文,广告屏蔽插件可能会导致该功能失效(如失效,请关闭广告屏蔽插件后再试):问题:I put a zip file in the android assets. How do i extract the file in the android internal storage? I know how to get the file, but i dont know how t…

Eclipse安装ADT失败解决办法

Eclipse的版本是3.5.2,配置Android的开发环境时遇到问题…… 按照Android官方文档一步步安装,到了安装Eclipse的ADT插件时,提示“requires org.eclipse.gef 0.0.0 but it could not be found” 缺少GEF,Eclipses Graphic Editing …

DM3730 LCD控制器驱动框架

一般来说,linux的LCD控制器驱动是分两个层次 1) fbmem.c 一个linux内核通用的LCD控制器层,没有任何硬件信息,而且不创建设备文件。 它提供的最重要的接口函数是register_framebuffer 2) 特定芯片的LCD控制器硬件驱动代码,他来调…

html仿qq最小化怎么实现,JS仿QQ好友列表展开、收缩功能(第一篇)

JS仿QQ好友列表展开、收缩功能(第一篇)发布时间:2020-10-17 14:20:03来源:脚本之家阅读:96作者:erdouzhang效果图如下所示:html:我的好友张三李四...企业好友小明小红...黑名单哈哈...css:ul,h3 {padding: …

Visual Studio 选择相同变量高亮

前段时间一直在使用matlab,今天需要使用vs2008,而用惯了matlab,习惯了其中一项选中变量高亮的设置,突然回来使用VS,感到各种不适应,顿时想到了一个词:矫情 呵呵,于是在网上找各种插件…

V210调整根分区大小

1. 修改uboot common/mmc_cmd_fdisk.c #define SYSTEM_PART_SIZE (120*1024*1024) 将120改成256 2. 在dd文件系统的时候,增大count dd if/dev/zero ofrootfs_qt4.ext3 bs1024 count262144 重烧系统的时候,需要先烧入uboot,然后重启再烧入…

html中怎么写jq,用jQuery替换HTML页面中的文本

如何替换jQuery中的任何字符串?假设我有一个字符串"-9o0-9909",我想用另一个字符串替换它。在问问题之前如何使用jQuery将HTML块替换为HTML块的可能重复,最好检查一下系统在输入问题标题时提出的自动建议您能否详细说明为什么您认为…

asp.net使用post方式action到另一个页面,在另一个页面接受form表单的值!(报错,已解决!)...

asp.net使用post方式action到另一个页面,在另一个页面接受form表单的值!(报错,已解决!) 原文:asp.net使用post方式action到另一个页面,在另一个页面接受form表单的值!(报…

Qt中translate、tr关系 与中文问题

Qt中translate、tr关系 与中文问题2010-09-22 00:15题外话:何时使用 tr ? 在论坛中漂,经常遇到有人遇到tr相关的问题。用tr的有两类人: (1)因为发现中文老出问题,然后搜索,发现很多人用tr,于是他…

html打印边距影响内容大小,关于web打印的问题,如何控制纸张大小和页边距

关于这个问题我上网查了很多资料,最后参照一个资料。编写了下面内容:但是根本达不到要求,哪位大侠有真正使用的经验?告诉我到底应该怎样弄?求一个真正使用的方法,谢谢!再就是这一行在visual stu…

win32控制台

可回显的调用方法: 这个方法步骤比较复杂,是通过创建一个新进程来模拟cmd命令行,将写命令行和回显通过管道的方式呈现。 例如: view plain 1. void CTestMFCDlg::OnOK() 2. { 3. // TODO: Add extra validation …

html是前段还是后端,javascript属于前端还是后端?

JavaScript是一种属于网络的脚本语言,已经被广泛用于Web应用开发,常用来为网页添加各式各样的动态功能,为用户提供更流畅美观的浏览效果。通常JavaScript脚本是通过嵌入在HTML中来实现自身的功能的。前端开发和后端开发的区别在于&#xff1a…

ubuntu12.04中shell脚本无法使用source的原因及解决方法

现象: shell脚本中source aaa.sh时提示 source: not found 原因: ls -l which sh 提示/bin/sh -> dash 这说明是用dash来进行解析的。 改回方法: 命令行执行:sudo dpkg-reconfigure dash 在界面中选择no 再ls -l which sh 提…

2021年河北省高考成绩录取查询结果,2021年河北高考一本录取结果查询和录取通知书发放时间...

河北高考一本录取结果查询和录取通知书发放时间从河北教育考试院获悉,河北高考成绩查询时间已经确定。同时,考生、家长关心的各批次录取时间也已出炉。其中,本科一批高等学校录取时间安排如下:本科一批第一志愿录取结束时间为7月1…

viewgroup 渲染过程

参考 http://blog.csdn.net/luoshengyang/article/details/8372924 总体步骤 performTraversals-->measure---->layout----->draw 测量布局渲染 1.measure 测量过程 例子:FrameLayout measure 测量开始判读是否需要测量 onMeasure 求实际宽度 measureChi…

C++读取ini文件的类

C读取ini文件的类 取自:http://www.viksoe.dk/code/all_mfc.htm,里面有各种MFC常用的类 // Ini.h: interface for the CIni class. // // Written by Bjarke Viksoe (bjarkeviksoe.dk) // Copyright (c) 2000. // // This code may be used in compiled …

A20(emmc) 编译环境

1. 需要物理内存3G,或者调高虚拟内存,否则编译会报错(killed) 2. 安装jdk 3. apt-get install bison apt-get install flex apt-get install gperf apt-get install libswitch-perl apt-get install libxml2-utils