EntropyMixer 就是是以前的EntropyService,生成随机数的一个东西。随机数一般与密码,加密等相关。
public EntropyMixer(String entropyFile, String randomDevice) {
if (randomDevice == null) { throw new NullPointerException("randomDevice"); }
if (entropyFile == null) { throw new NullPointerException("entropyFile"); }
this.randomDevice = randomDevice;
this.entropyFile = entropyFile;
loadInitialEntropy(); //通过RandomBlock给/dev/urandom 喂数据
addDeviceSpecificEntropy(); //给/dev/urandom 喂一些特殊的数据
writeEntropy(); // 将数据写回entropy.dat
scheduleEntropyWriter();//3h 写一次
}
Linux内核采用熵来描述数据的随机性。熵(entropy) 是描述系统混乱无序程度的物理量,一个系统的熵越大则说明该系统的有序性越差,即不确定性越大。在信息学中,熵被用来表征一个符号或系统的不确定性,熵越大,表明系统所含有用信息量越少,不确定度越大。
怎样理解这里的噪声?environmental noise, 从物理角度看,噪声是发声体做无规则振动时发出的声音。这里要的就是“无规则”。
/dev/random && /dev/urandom : 前者在entropy pool为空的时候会block,速度也慢了不少,但随机数序列质量更高,适合于高强度的加密算法
如何查看当前熵值?Linux内核中当前熵的值和大小可以通过访问/proc/sys/kernel/random/得到
伪随机数:
C语言中伪随机数生成算法实际上是采用了"线性同余法”。具体的计算如下:
Xi = (Xi-1 * A + C ) mod M
其中A,C,M都是常数(一般会取质数)。当C=0时,叫做乘同余法。引出一个概念叫seed,它会被作为X0被代入上式中,然后每次调用rand()函数都会用上一次产生的随机值来生成新的随机值。可以看出实际上用rand()函数生成的是一个递推的序列,一切值都来源于最初的 seed。所以当初始的seed取一样的时候,得到的序列都相同。
C语言里面有RAND_MAX这样一个宏,定义了rand()所能得到的随机值的范围。在C里可以看到RAND_MAX被定义成0x7fff,也就是32767。rand()函数里递推式中M的值就是32767。
线性同余法生成的是伪随机数,粗略符合均匀分布。根据中心极限定理,任何分布的噪声,通过反复相加,就可以成为高斯噪声。
例:
unsigned int random(void){
RAND_SEED=(RAND_SEED*123+59)%65536;
return(RAND_SEED);
}
怎样使用/dev/urandom 产生随机数:
转于 http://www.groad.net/bbs/read.php?tid-7194.html
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <math.h>
int
main (
int
argc,
char
*argv[])
{
FILE
*urandom;
unsigned
int
seed;
int
i;
urandom =
fopen
(
"/dev/urandom"
,
"r"
);
if
(urandom == NULL) {
fprintf
(stderr,
"Cannot open /dev/urandom!\n"
);
exit
(EXIT_FAILURE);
}
for
(i = 0; i < 10; i++) {
fread
(&seed,
sizeof
(seed), 1, urandom);
srand
(seed);
printf
(
"Random number from 1 to 100: %d\n"
, (
int
)
floor
(
rand
() * 100.0 / ((
double
) RAND_MAX + 1) )+ 1);
}
return
0;
}