为什么盐被包含在用C crypt函数哈希

问题描述:

看这个很基本的C程序:为什么盐被包含在用C crypt函数哈希

#include <stdio.h> 
#include <stdlib.h> 
#include <string.h> 
#include <sys/types.h> 
#include <unistd.h> 
#include <crypt.h> 

int main (int argc, char *argv[]) 
{ 
    char pid[16]; 
    int id; 
    for (id = 0; id < 100; id++) 
    { 
     snprintf(pid, sizeof(pid), "%i", id); 
     printf("%s %s\n",pid, crypt(pid, "$1$awesome")); 
    } 
} 

这里是Linux系统上的输出:

0 $1$awesome$cVjo4Ue9HeJs7sStMTm6v. 
1 $1$awesome$6.658tD5uVqwQJ6/S8Mc71 
2 $1$awesome$bKavcHTWRGnlTgP.zTZhO. 
3 $1$awesome$ZlBH.fgxGrfw/naq38hyv. 
4 $1$awesome$aQCliN7gPud1PC07Vri.y1 
5 $1$awesome$EewcRVU39I/n0uMGaDxCN0 
6 $1$awesome$fKMRDZaa5wra4G8xy9.m0/ 
7 $1$awesome$AqJ0SmXImg.xcUg/Yh/ov. 
8 $1$awesome$bT3Wq9QORw1dnNZFZmVBk. 
9 $1$awesome$4uM8mfZGdj2zeZ/CP/GSz1 
10 $1$awesome$Gsa/ilcFg1LRl2dqNhgXg0 

我不明白为什么盐在输出中可见。 我试图在Mac OS X上编译相同的程序,但没有看到散列中的盐。 这不是一个安全漏洞吗?我们不应该在哈希中清楚地看到盐?

感谢

+9

不,这不是安全漏洞。您需要存储盐以便能够散列下一个输入并进行比较。盐的目的是迫使攻击者单独处理每个密码,而不是一个秘密。你用同样的盐来解决这个问题。它应该是随机的。见例如https://security.stackexchange.com/questions/51959/why-are-salted-hashes-more-secure-for-password-storage – jonrsharpe

+1

一种重要的注意:'crypt'功能是不是C标准的一部分。它是[POSIX标准]的一部分(http://pubs.opengroup.org/onlinepubs/9699919799/functions/crypt.html)。 –

+0

盐不** **不必须保持秘密见:[隐藏盐的哈希的必要性(https://*.com/questions/213380/the-necessity-of-hiding-the-盐换一个散列)。 –

阅读从谁最初提出它的研究人员section 3。它说什么@jonrsharpe在上面的评论说,但总是很高兴得到原始源(重点煤矿):

关键搜索技术仍可能当它在一个用于打开了几个密码 大量的密码集合,并且似乎明智地使这个任务尽可能地困难。为此,当第一次输入密码 时,密码程序获得一个12位 随机数(通过读取实时时钟)并将其附加到 用户输入的密码。连接的字符串是 加密的,并且加密的12位随机数(称为盐)和64位结果都被输入到密码 文件中。

当用户稍后登录到系统时,将从密码文件中提取12位数量并附加到输入的密码。 与以前一样,加密结果与密码文件中剩余的64位中的 相同。 这个修改不会增加查找任何个人密码的任务,从 开始,但现在测试给定字符串的工作对 大量的加密密码已经乘以4,096, (2^12)。原因是每个密码有4,096个加密版本 ,其中一个已被系统随机挑选或多或少地选取 。

通过这种修改,坏人可能会花费几天的时间在计算机上试图在具有数百个密码的 密码的系统上找到密码,并且根本找不到任何密码。更重要的是事实上,事先准备一个加密的字典是不切实际的。 这样的加密字典可以用来在 毫秒出现时破解新密码。

此修改存在(无意)的副作用。 变得几乎不可能找出在两个或多个系统上使用密码为 的人是否在所有人身上都使用了相同的密码,除非您已经知道这一点,否则 。