国密随机数检测--1/15 单比特频数检测

最近研究随机数检测,主要学习了一下NIST和国密检测,这里整理了国密15项检测规项目的原理,数学表达式以及python源码。

15项检测项目分别为单比特频数检测、块内频数检测、扑克检测、重叠子序列检测、游程总数检测、游程分布检测、块内最大“1”游程检测、二元推导检测、自相关检测、矩阵秩检测、累加和检测、近似熵检测、线性复杂度检测、 Maurer通用统计检测、离散傅立叶检测。

规定了商用密码应用中的随机性检测指标和检测方法,适用于对随机数发生器产生的二元序列的随机性检测。

-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

1/15 单比特频数检测  monobit frequency test

a) 将待检序列ε 中的 0 和 1 分别转换成-1 和 1, X i = 2εi -1  (1 i n ≤ )

b) 对其累加求和得

c) 计算统计值

 

d) 计算

erfc为余误差函数。

 

e) 如果

 

 则认为待检测序列通过但比特数检测。

 

原理:

单比特频数检测是最基本的检测,用来检测一个二元序列中0和1的个数是否相近。也就是说,若已知一个长度为n的二元序列,检测改序列是否有较好的0、1平衡性。令n0、n1分别表示该序列中0和1的数目。对一个随机序列,当其长度充分大时,其统计值V应该服从正态分布

 

 

参数要求:

n>100 

 

不通过分析:

0或1个数太小

 

测试demo

import math

def count_ones_zeroes(bits):
    ones = 0
    zeroes = 0
    for bit in bits:
        if (bit == 1):
            ones += 1
        else:
            zeroes += 1
    return (zeroes,ones)

def monobit_test(bits):
    n = len(bits)
    
    zeroes,ones = count_ones_zeroes(bits)
    s = abs(ones-zeroes)
    print ("  Ones count   = %d" % ones)
    print ("  Zeroes count = %d" % zeroes)
    
    p = math.erfc(float(s)/(math.sqrt(float(n)) * math.sqrt(2.0)))
    
    success = (p >= 0.1)
    return (success,p,None)

bits=[1,1,0,1,0,0,1,1,0,1,0,1,0,1,0,1,1,0,0,1,0,1,1,1,1,1,
          0,1,1,1,1,1,0,0,1,1,1,0,1,1,1,1,1,0,1,1,1,1,1,0,0,0,0,
          0,0,0,0,0,1,0,0,0,1,0,0,0,0,1,1,0,0,1,0,0,0,0,1,0,1,0,
          0,1,1,0,0,0,1,1,1,0,1,0,0,0,0,1,0,0,1,0,1,0,1,0,0,1,1,
          0,0,0,1,1,0,1,0,1,1,1,0,0,1,1,1,1,1,0,0,0] 


if __name__ == "__main__":
    s1,s2,s3= monobit_test(bits)
    print(s1)
    print("p value is %s" %s2)

 

 

 

 

 

 

 

 

 

 

posted @ 2020-04-23 09:25  In.the.peace  阅读(2597)  评论(0编辑  收藏  举报