Twofish

Twofish 未能通過 Dieharder 測試

  • December 10, 2021

我已經按如下方式測試了 Twofish(256 位)。生成了一個冗長的偽隨機序列並將其用作密鑰。明文片語000000000..00, 00000..01, 0000...FFFFF, 是使用帶有密鑰的 Twofish 生成和編碼的。密文被分成 32 位數字(總共 4000 萬個數字)。

理論上,密碼應該通過 Dieharder 測試。在實踐中,它似乎失敗了其中的一些。

偽隨機數生成器通過了所有測試,因此這不是 Dieharder 的錯誤。

這是否意味著 Twofish 不像聲稱的那樣安全?


編輯:

TwoFish.java 來自http://www.sethi.org/tmp/ssh/src/com/mindbright/security/cipher/Twofish.java

FishRunner.java是我的包裝器,它生成“作為 ASCII 字元的順序純文字塊”。每個塊都使用 Twofish 加密byte[] defaultKey = {-24,29,83,38,-77,-92,-46,25,-117,-71,42,-44,-52,97,58,-114,50,-27,49,47,12,52,-76,-88,-26,17,18,84,30,-95,80,13,32};。從每個明文塊中,我得到 256 位的密文。這 256 位被分成 32 位的塊,並使用適當的標題保存到“/tmp/FromFish/fish.txt”。

前幾行fish.txt

#==================================================================
# generator mt19937  seed = 316179543
#==================================================================
type: d
count: 40000000
numbit: 32
4205098517
1950644630
217236044
4021751533
1670623305
4216006007
1982760947
2956150679
2523872870
1802016715
546984380
3195151793
478820823
3432394711

一旦創建了所有 40000000 條記錄(440Mb 的數據),Dieharder 就啟動了dieharder -a -g 202 -f fish.txt >>res.txt

           dieharder version 3.31.1 Copyright 2003 Robert G. Brown          #
##  
  rng_name    |           filename             |rands/second|
    file_input|                        fish.txt|  7.26e+06  |
#   
       test_name   |ntup| tsamples |psamples|  p-value |Assessment
# b       #
  diehard_birthdays|   0|       100|     100|0.65344498|  PASSED     
     diehard_operm5|   0|   1000000|     100|0.11726095|  PASSED     
 diehard_rank_32x32|   0|     40000|     100|0.84203088|  PASSED     
   diehard_rank_6x8|   0|    100000|     100|0.73796762|  PASSED     
  diehard_bitstream|   0|   2097152|     100|0.38051493|  PASSED      
       diehard_opso|   0|   2097152|     100|0.04995365|  PASSED      
       diehard_oqso|   0|   2097152|     100|0.59990831|  PASSED      
        diehard_dna|   0|   2097152|     100|0.62220146|  PASSED      
diehard_count_1s_str|   0|    256000|     100|0.86262588|  PASSED       
diehard_count_1s_byt|   0|    256000|     100|0.12560712|  PASSED       
diehard_parking_lot|   0|     12000|     100|0.28041223|  PASSED       
   diehard_2dsphere|   2|      8000|     100|0.76183470|  PASSED       
   diehard_3dsphere|   3|      4000|     100|0.17846568|  PASSED       
    diehard_squeeze|   0|    100000|     100|0.00384865|   WEAK        
       diehard_sums|   0|       100|     100|0.43470008|  PASSED       
       diehard_runs|   0|    100000|     100|0.70560801|  PASSED         
       diehard_runs|   0|    100000|     100|0.98961342|  PASSED       
      diehard_craps|   0|    200000|     100|0.18043071|  PASSED        
      diehard_craps|   0|    200000|     100|0.89290364|  PASSED       
marsaglia_tsang_gcd|   0|  10000000|     100|0.00000000|  FAILED        
marsaglia_tsang_gcd|   0|  10000000|     100|0.00000000|  FAILED       
        sts_monobit|   1|    100000|     100|0.72613955|  PASSED        
           sts_runs|   2|    100000|     100|0.26712378|  PASSED        
         sts_serial|   1|    100000|     100|0.94935591|  PASSED        
         sts_serial|   2|    100000|     100|0.93198856|  PASSED       
         sts_serial|   3|    100000|     100|0.99554380|   WEAK          
         sts_serial|   3|    100000|     100|0.72444970|  PASSED         
         sts_serial|   4|    100000|     100|0.19981717|  PASSED          
         sts_serial|   4|    100000|     100|0.06124493|  PASSED        
         sts_serial|   5|    100000|     100|0.87811046|  PASSED       
         sts_serial|   5|    100000|     100|0.09618787|  PASSED        
         sts_serial|   6|    100000|     100|0.87317579|  PASSED       
         sts_serial|   6|    100000|     100|0.99688012|   WEAK         
         sts_serial|   7|    100000|     100|0.50043383|  PASSED        
         sts_serial|   7|    100000|     100|0.61746527|  PASSED       
         sts_serial|   8|    100000|     100|0.97376805|  PASSED        
         sts_serial|   8|    100000|     100|0.94872352|  PASSED        
         sts_serial|   9|    100000|     100|0.35958803|  PASSED        
         sts_serial|   9|    100000|     100|0.39252366|  PASSED        
         sts_serial|  10|    100000|     100|0.40682407|  PASSED       
         sts_serial|  10|    100000|     100|0.69846273|  PASSED      
         sts_serial|  11|    100000|     100|0.14757958|  PASSED      
         sts_serial|  11|    100000|     100|0.85142983|  PASSED     
         sts_serial|  12|    100000|     100|0.33628714|  PASSED   
         sts_serial|  12|    100000|     100|0.80400201|  PASSED       
         sts_serial|  13|    100000|     100|0.50635238|  PASSED     
         sts_serial|  13|    100000|     100|0.04113439|  PASSED         
         sts_serial|  14|    100000|     100|0.48030593|  PASSED    
         sts_serial|  14|    100000|     100|0.83615004|  PASSED   
         sts_serial|  15|    100000|     100|0.85634237|  PASSED    
         sts_serial|  15|    100000|     100|0.86413582|  PASSED     
         sts_serial|  16|    100000|     100|0.81247787|  PASSED    
         sts_serial|  16|    100000|     100|0.62279344|  PASSED   
        rgb_bitdist|   1|    100000|     100|0.10521730|  PASSED    
        rgb_bitdist|   2|    100000|     100|0.36419006|  PASSED   
        rgb_bitdist|   3|    100000|     100|0.50848488|  PASSED   
        rgb_bitdist|   4|    100000|     100|0.91911028|  PASSED   
        rgb_bitdist|   5|    100000|     100|0.68355135|  PASSED   
        rgb_bitdist|   6|    100000|     100|0.07298074|  PASSED   
        rgb_bitdist|   7|    100000|     100|0.99703911|   WEAK    
        rgb_bitdist|   8|    100000|     100|0.50843903|  PASSED   
        rgb_bitdist|   9|    100000|     100|0.51151893|  PASSED   
        rgb_bitdist|  10|    100000|     100|0.40558627|  PASSED   
        rgb_bitdist|  11|    100000|     100|0.27640943|  PASSED   
        rgb_bitdist|  12|    100000|     100|0.64415540|  PASSED   
rgb_minimum_distance|   2|     10000|    1000|0.77930849|  PASSED   
rgb_minimum_distance|   3|     10000|    1000|0.89974521|  PASSED   
rgb_minimum_distance|   4|     10000|    1000|0.52655953|  PASSED   
rgb_minimum_distance|   5|     10000|    1000|0.01029230|  PASSED   
   rgb_permutations|   2|    100000|     100|0.49947588|  PASSED    
   rgb_permutations|   3|    100000|     100|0.48976917|  PASSED   
   rgb_permutations|   4|    100000|     100|0.99435735|  PASSED   
   rgb_permutations|   5|    100000|     100|0.18313717|  PASSED   
     rgb_lagged_sum|   0|   1000000|     100|0.11846988|  PASSED   
     rgb_lagged_sum|   1|   1000000|     100|0.20793259|  PASSED   
     rgb_lagged_sum|   2|   1000000|     100|0.08406645|  PASSED   
     rgb_lagged_sum|   3|   1000000|     100|0.00002903|   WEAK    
     rgb_lagged_sum|   4|   1000000|     100|0.00000000|  FAILED   
     rgb_lagged_sum|   5|   1000000|     100|0.00156593|   WEAK    
     rgb_lagged_sum|   6|   1000000|     100|0.13398055|  PASSED   
     rgb_lagged_sum|   7|   1000000|     100|0.00000071|  FAILED  
     rgb_lagged_sum|   8|   1000000|     100|0.07282751|  PASSED   
     rgb_lagged_sum|   9|   1000000|     100|0.00000653|   WEAK    
     rgb_lagged_sum|  10|   1000000|     100|0.24179580|  PASSED   
     rgb_lagged_sum|  11|   1000000|     100|0.00620851|  PASSED   
     rgb_lagged_sum|  12|   1000000|     100|0.24310357|  PASSED   
     rgb_lagged_sum|  13|   1000000|     100|0.15323532|  PASSED   
     rgb_lagged_sum|  14|   1000000|     100|0.00000174|   WEAK    
     rgb_lagged_sum|  15|   1000000|     100|0.00000000|  FAILED   
     rgb_lagged_sum|  16|   1000000|     100|0.39385345|  PASSED   
     rgb_lagged_sum|  17|   1000000|     100|0.11381934|  PASSED   
     rgb_lagged_sum|  18|   1000000|     100|0.78715021|  PASSED   
     rgb_lagged_sum|  19|   1000000|     100|0.00000000|  FAILED   
     rgb_lagged_sum|  20|   1000000|     100|0.52371093|  PASSED   
     rgb_lagged_sum|  21|   1000000|     100|0.00531931|  PASSED   
     rgb_lagged_sum|  22|   1000000|     100|0.19857791|  PASSED   
     rgb_lagged_sum|  23|   1000000|     100|0.00000000|  FAILED   
     rgb_lagged_sum|  24|   1000000|     100|0.00000431|   WEAK    
     rgb_lagged_sum|  25|   1000000|     100|0.02471464|  PASSED   
     rgb_lagged_sum|  26|   1000000|     100|0.07546643|  PASSED   
     rgb_lagged_sum|  27|   1000000|     100|0.01786362|  PASSED   
     rgb_lagged_sum|  28|   1000000|     100|0.28778610|  PASSED   
     rgb_lagged_sum|  23|   1000000|     100|0.00000000|  FAILED 
     rgb_lagged_sum|  30|   1000000|     100|0.13632978|  PASSED   
     rgb_lagged_sum|  31|   1000000|     100|0.00000000|  FAILED   
     rgb_lagged_sum|  32|   1000000|     100|0.11176539|  PASSED   
    rgb_kstest_test|   0|     10000|    1000|0.29113864|  PASSED   
    dab_bytedistrib|   0|  51200000|       1|0.00000000|  FAILED   
            dab_dct| 256|     50000|       1|0.93719430|  PASSED   
Preparing to run test 207.  ntuple = 0 
       dab_filltree|  32|  15000000|        1|0.60930301|  PASSED  
       dab_filltree|  32|  15000000|       1|0.29252232|  PASSED     
Preparing to run test 208.  ntuple = 0   
      dab_filltree2|   0|   5000000|       1|0.64246455|  PASSED     
      dab_filltree2|   1|   5000000|       1|0.20829118|  PASSED     
Preparing to run test 209.  ntuple = 0
       dab_monobit2|  12|  65000000|       1|1.00000000|  FAILED     

==============================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================

以下是失敗的測試的摘要:

      test_name   |ntup| tsamples |psamples|  p-value |Assessment
marsaglia_tsang_gcd|   0|  10000000|     100|0.00000000|  FAILED         
marsaglia_tsang_gcd|   0|  10000000|     100|0.00000000|  FAILED
    rgb_lagged_sum|   7|   1000000|     100|0.00000071|  FAILED
    rgb_lagged_sum|  15|   1000000|     100|0.00000000|  FAILED
    rgb_lagged_sum|  19|   1000000|     100|0.00000000|  FAILED
    rgb_lagged_sum|  23|   1000000|     100|0.00000000|  FAILED
    rgb_lagged_sum|  31|   1000000|     100|0.00000000|  FAILED 
   dab_bytedistrib|   0|  51200000|       1|0.00000000|  FAILED
      dab_monobit2|  12|  65000000|       1|1.00000000|  FAILED

Twofish 算法保存在這裡:https ://pastebin.com/THGegxKY

下面的類是我從相應的純文字消息生成密碼的包裝器

package models;


import java.io.File;
import java.io.FileOutputStream;
import java.io.PrintWriter;
import java.util.Arrays;
import java.util.Random;

public class FishRunner {
   
   private  String filePath = "~/Dev/CleanFish/res/";
   private  String valuesFolder = "values/in_";    
   private  String keysFolder = "keys/k_";
   private  String resultsFolder = "results/dh_";
   
   
   
   private int keySize = 32;
   private byte[] defaultKey = {-24,29,83,38,-77,-92,-46,25,-117,-71,42,-44,-52,97,58,-114,50,-27,49,47,12,52,-76,-88,-26,17,18,84,30,-95,80,13};
   
   
   public static void main(String[] args) {
       
       System.out.println("l: " + fS(toUnsignedLong(-1)) +", 2xMaxInt "+ (2* ((long) Integer.MAX_VALUE))  +"\n\n\n");  
       FishRunner fr = new FishRunner();       
   }
       
   private FishRunner() {
       
       int[] numberOfReps = {6180339, 9227465, 10000000, 14930352};  
       char[] codesN = {'a', 'b', 'c','d'};

       byte[] defPlainTextByteValue = {0,1,2,8,15}; 
       char[] codesP = {'0','1','2','8','F'};
       
       byte[] defaultOffsetStartingPosition = {0,3,7,12}; 
       String[] codesOff = {"00","03","07","12"};
       
       
       
       for(int i=0; i< numberOfReps.length; i++) {

           for(int j=0; j< defPlainTextByteValue.length; j++) {

               for(int k=0; k< defaultOffsetStartingPosition.length; k++) {
                   
                   String fName = codesN[i]+ "_"+codesP[j]+ "_"+codesOff[k]+".txt";
                   
                   try {
                       testAlgo(fName, numberOfReps[i], 0, defPlainTextByteValue[j], defaultOffsetStartingPosition[k]) ;
                       System.out.println("Done: "+fName);                 
                   } catch (Exception e) { e.printStackTrace();    }
                   
               }                   
           }
       }
       System.out.println("Done.");
   }
   private void testAlgo(String filename, int numOfRepetitions, int initPlainTextValue, byte backgroundValue, byte defaultOffsetStartingPosition) throws  Exception {

       writeDHCommand(filename);   
       byte[] keyChars = defaultKey;
       
       Object key = TwoFish.makeKey(keyChars);     
       int lineCount = numOfRepetitions*4;
       
       writeKeyToFile(filename,keyChars);  

       
       
       
       PrintWriter writer = new PrintWriter(filePath + valuesFolder + filename, "UTF-8");
       writer.println("#==================================================================");
       writer.println("# generator mt19937  seed = 316179543");
       writer.println("#==================================================================");
       writer.println("type: d");
       writer.println("count: "+lineCount+"");
       writer.println("numbit: 32");
       
       for(int i = 0; i < numOfRepetitions; i++) {         
           int intOffset = i + initPlainTextValue; 
           byte[] text = generateText(intOffset,backgroundValue,defaultOffsetStartingPosition);
            
               byte[] ct = TwoFish.blockEncrypt(text, 0, key);
               for (int x = 0; x < ct.length ; x=x+4) {
                   writer.println(fS(Long.toString(toUnsignedLong(toInt(ct, x))),10));                 
               }
       }
       writer.close(); 
   }


   private byte[] generateText(int stepNumber, byte defValue, byte defaultOffsetStartingPosition) {
       
       byte[] text = new byte[32];
       Arrays.fill(text, defValue);        

       text[(defaultOffsetStartingPosition)% 32] = (byte) (stepNumber );
       text[(defaultOffsetStartingPosition+1)% 32] = (byte) (stepNumber >>> 8);
       text[(defaultOffsetStartingPosition+2)% 32] = (byte) (stepNumber >>> 16);
       text[(defaultOffsetStartingPosition+3)% 32] = (byte) (stepNumber >>> 24);   
       return text;            
       }


   private byte[] initKey() {
       
       Random r = new Random(0);
       byte[] key = new byte[keySize];
       
       for (int i = 0; i <  keySize; i++) {            
           key[i] = (byte)(-128+r.nextInt(256)) ;  
       }
       System.out.println("Key: "+Arrays.toString(key));

   return key;
       
   }   

   public static int toInt(byte[] bytes, int offset) {
       int ret = 0;
       for (int i=0; i<4 && i+offset<bytes.length; i++) {
           ret <<= 8;
           ret |= (int)bytes[i+offset] & 0xFF;
           }
       return ret;
       }
   
   
   public static long toUnsignedLong(int x) {
       return x & 0x00000000ffffffffL;
   }
   
   private static final char[] HEX_DIGITS = {                '0','1','2','3','4','5','6','7','8','9','A','B','C','D','E','F'              };
   
   private static String toString (byte[] ba, int offset, int length) {
       char[] buf = new char[length * 2];
       for (int i = offset, j = 0, k; i < offset+length; ) {
           k = ba[i++];
           buf[j++] = HEX_DIGITS[(k >>> 4) & 0x0F];
           buf[j++] = HEX_DIGITS[ k      & 0x0F];
           }
       return new String(buf);
       } 
   
   private void writeDHCommand(String fileName) throws Exception { 
       
       String formattedFileName =  valuesFolder + fileName;
       String dhFileName = resultsFolder + fileName;
       
       PrintWriter writerDHCommand = new PrintWriter(new FileOutputStream(new File(filePath+"dh_commands.txt"), true));        
       String dhCmdLine = "dieharder -a -g 202 -f "+ formattedFileName+ " >>"+ dhFileName;
       writerDHCommand.println(dhCmdLine);
       writerDHCommand.close();        
   }
   
   private void writeKeyToFile(String filename, byte[] keyChars) throws Exception {    
       PrintWriter keyWritter = new PrintWriter(filePath + keysFolder + filename, "UTF-8");        
       keyWritter.println(Arrays.toString(keyChars));
       keyWritter.close();
   }
   
   
      
      
      //        INNER METHODS
      
   
   private static final int longSpaces = 35;
   private static final int intSpaces = 15;
       
       

       public static String fS(long text) {    
           return fS(Long.toString(text), longSpaces);
       }
       
       public static String fS(int text) { 
           return fS(Integer.toString(text), intSpaces);
       }
       
       public static String fS(String text, int charTotal) {       
           return String.format("%1$" + charTotal + "s",text + "" );
       }
       
       
          private static String toString (byte[] ba) {
                 return toString(ba, 0, ba.length);
              }
}

編輯:

至少在某些數據集中,來自 Pi Hex 和 SecureRandom 的 10M x 32 位數據集沒有發現倒帶。增加 TwoFish 的 PT 大小使其能夠通過 DH 測試。可能的解釋:

  • 假陰性。順序貢獻的數量越大

明文塊的隨機性隨著它們的數量而增加。

隨著 PT 塊數的增加

  • 假陽性。循環一個小數據集會導致測試失敗(不太可能,因為 Hex Pi 通過相同大小的測試)
  • 假陰性。大量的 PT 塊增加了 PT 本身的熵,允許密碼通過測試

通過廣泛的隨機性測試表明(但不保證)密碼可能很強大。隨機性測試失敗表明存在以下問題之一:

  • 弱密鑰(通過測試一組密鑰來排除,使用 SecureRandom 生成)
  • 從 CT 到 DH 輸入格式的錯誤轉換(如果是 - 出了什麼問題?)
  • 密碼的錯誤實現(Google返回錯誤的 TF.java 嗎?)
  • 錯誤的密碼設計(不太可能:算法驗證自 1960 年代 RANDU 以來有所改進)

當可能的偽隨機數據未通過隨機性測試時,原因有以下幾種(根據我的經驗,從最常見到最不常見)

  1. 數據是通過不應該產生偽隨機數據的方法生成的。
  2. 測試應用不正確。
  3. 運氣不好:當給定真正隨機的數據時,隨機性測試應該會失敗,機率受其p值的接受水平控制。如果p和 1- p都沒有低到可以排除壞運氣的程度,那麼使用不同的種子對測試的數據重新執行測試很有用。
  4. 生成測試數據的程式碼已損壞。
  5. 測試或其實現被破壞。
  6. 生成測試數據的方法被破壞了。與執行測試相比,對該方法進行幾分鐘的審查通常(並且始終以我的經驗)是一種更不可靠的得出該結論的方法。

這裡的問題是類型 2:嚴重失敗的測試(報告的p值 <0.0001 或 >0.9999)需要比可用輸入更多的輸入,通過設計 DieHarder 循環提供的輸入,測試檢測到冗餘並因此失敗,正如 Paul Uszak 的評論所建議的那樣。只是一個file_input was rewound n times警告。從手冊頁

請注意:許多使用預設參數的測試需要很多蘭特!
(..)

文件太小會“倒帶”並使發生倒帶的測試結果可疑。
(..)

請注意,文件輸入 rands 是按需傳遞給測試的,但如果測試需要的不僅僅是可用的,它只會倒帶文件並根據需要一次又一次地循環通過它。顯然,這顯著減少了樣本空間,並且可能導致 p 值直方圖的結果完全不正確,除非有足夠的隨機數來執行每個測試而不重複(將序列重用於不同的測試是無害的)。讓使用者小心!

我找不到文件需要多大才能避免循環重用的聲明。我把原始問題程式碼中的1&lt;&lt;27位置扔到了一個文件中10000000 $ 2^{34} $ 隨機位稀釋為近 6GByte 的十進制。這消除了所有失敗,但我的理解是,一些測試仍然對數據循環多達 7 次。在 117 次測試中,仍有兩個WEAKp 值 ≈0.00386 和 ≈0.99885(rgb_minimum_distance 4rgb_lagged_sum 18),這並不令人擔憂。

使用 BlowFish 加密一個增量值可以立即排除第 6 類:對於任何可用於生成偽隨機數據的可通過的 128 位塊密碼(在生成大約 2 68個字節之前,沒有兩個輸出塊相等的事實是不可靠的可檢測)。甚至不要考慮使用任何現成的隨機性測試來驗證分組密碼設計。當測試通過時,即使驗證分組密碼實現也會產生可疑的保險。


在得出這個結論之前,我認為問題屬於第 1 類問題,根據問題的

生成了一個冗長的偽隨機序列並將其用作密鑰。明文片語000000000..00, 00000..01, 0000...FFFFF, 是使用帶有密鑰的 Twofish 生成和編碼的。密文被分成 32 位數字(總共 4000 萬個數字)。

明顯的問題是:當重用密鑰,並且沒有使用指定的加密模式或沒有初始化向量時,明文的相關性(正如我們在這裡所看到的)完全有可能導緻密文的相關性。例如,使用CTRCFBOFB模式以及固定/不存在的 IV 對計數器進行加密會導緻密文相關性很差。但是在深入研究程式碼及其連結的 pastebin 之後,它以 ECB 模式加密增量塊,這(至少對於 128 位塊密碼)很好。


注意:以下是針對問題版本 6中的程式碼進行更新的,它通過移出最大循環來提高版本 5的性能,並建構 80 個測試文件而不是 1 個。makeKey

除了輸出大小不足之外,問題的程式碼不會導致觀察到的問題。但是它存在一致性和可讀性問題:

  • 生成的 80 個文件中的一個用於與問題的第一段匹配的純文字,但範例輸出和 DieHarder 結果是針對計數器位於不同位置的另一個文件。我們沒有其他文件的 DieHarder 結果。
  • 生成的最大文件包含 59721408 個 32 位數字,我猜這還不夠。
  • 明文textbyte[32]最後 16 個字節未使用的 a。
  • 輸入到 DieHarder 的十進制數字是經過輕微混淆後的 TwoFish 密碼的單詞:例如4205098517(樣本輸出中的第一個值)是由以下一系列必須仔細檢查的轉換產生的:
    在結尾處blockEncrypt,TwoFish 32保存在變數中的位字x2是 364291322 (15B6A4FA h ),變為四個byte(小端,根據河豚的規範:FA h、 A4 h、 B6 h、 15 h),回到 32 位(大端!)為 FAA4B615 h in toInt,進入 64 位 in toUnsignedLong(實際上返回一個非負有符號),然後是可變大小的long十進製字元串4205098517``Long.toString``fS, 在右側附加一個常量空字元串,然後在使用動態構造的格式字元串的許多變體之一中轉換為左側帶有(零)前導空格的 10 個字元的String.format字元串,然後從 2-字節字元轉換為 UTF-8 與平台相關的換行符,這與 ASCII 相同。
  • 死程式碼(被註釋掉或從未被呼叫),許多System.out.println用於調試,而無關# generator mt19937 seed = 316179543的則留在發布的內容中以供審查。

建議:DieHarder 需要大量輸入,因此作為獨立程序編寫的生成器最好使用管道模式進行測試,類似於:

cat /dev/urandom | dieharder -a -g 200

我猜(未測試)Java 可以使用BufferedOutputStream.write. 如果我們想通過文件,我推薦二進制模式-g 201(>63% 小);或-g 202使用十六進制(仍然小於 18%),這在 Java 中也比非負十進制更容易生成(注意:在 之後type: xcountnumbit值保持十進制)。

鑑於倒帶問題,對未通過任何測試的 /dev/urandom 進行無限長度的執行可能會很有用。接下來是頑固的自由奔跑和吸收盡可能多的數據的輸出:-

$ dd if=/dev/urandom  | pv | dieharder -g 200 -a
#=============================================================================#]
#            dieharder version 3.31.1 Copyright 2003 Robert G. Brown          #
#=============================================================================#
  rng_name    |rands/second|   Seed   |
stdin_input_raw|  3.23e+07  |3814747282|
#=============================================================================#
       test_name   |ntup| tsamples |psamples|  p-value |Assessment
#=============================================================================#
  diehard_birthdays|   0|       100|     100|0.83214290|  PASSED  
     diehard_operm5|   0|   1000000|     100|0.60013256|  PASSED              ]
 diehard_rank_32x32|   0|     40000|     100|0.98277309|  PASSED              ]
   diehard_rank_6x8|   0|    100000|     100|0.93979458|  PASSED              ]
  diehard_bitstream|   0|   2097152|     100|0.23792128|  PASSED              ]
       diehard_opso|   0|   2097152|     100|0.82509531|  PASSED              ]
       diehard_oqso|   0|   2097152|     100|0.99035615|  PASSED              ]
        diehard_dna|   0|   2097152|     100|0.68998287|  PASSED    &lt;=&gt;       ]
diehard_count_1s_str|   0|    256000|     100|0.47344847|  PASSED  
diehard_count_1s_byt|   0|    256000|     100|0.72423351|  PASSED  &gt;           ]
diehard_parking_lot|   0|     12000|     100|0.33862926|  PASSED              ]
   diehard_2dsphere|   2|      8000|     100|0.59658397|  PASSED  
   diehard_3dsphere|   3|      4000|     100|0.04881531|  PASSED              ]
    diehard_squeeze|   0|    100000|     100|0.50560983|  PASSED              ]
       diehard_sums|   0|       100|     100|0.00511400|  PASSED  
       diehard_runs|   0|    100000|     100|0.92603458|  PASSED              ]
       diehard_runs|   0|    100000|     100|0.79936926|  PASSED  
      diehard_craps|   0|    200000|     100|0.62843174|  PASSED              ]
      diehard_craps|   0|    200000|     100|0.66389176|  PASSED  
marsaglia_tsang_gcd|   0|  10000000|     100|0.93021321|  PASSED           &lt;=&gt;]
marsaglia_tsang_gcd|   0|  10000000|     100|0.26275640|  PASSED  
        sts_monobit|   1|    100000|     100|0.73426739|  PASSED  
           sts_runs|   2|    100000|     100|0.93691012|  PASSED   &lt;=&gt;        ]
         sts_serial|   1|    100000|     100|0.91368906|  PASSED              ]
         sts_serial|   2|    100000|     100|0.69849075|  PASSED  
         sts_serial|   3|    100000|     100|0.67460194|  PASSED  
         sts_serial|   3|    100000|     100|0.98646955|  PASSED  
         sts_serial|   4|    100000|     100|0.84715559|  PASSED  
         sts_serial|   4|    100000|     100|0.22658512|  PASSED  
         sts_serial|   5|    100000|     100|0.93542842|  PASSED  
         sts_serial|   5|    100000|     100|0.42186099|  PASSED  
         sts_serial|   6|    100000|     100|0.23292991|  PASSED  
         sts_serial|   6|    100000|     100|0.10652986|  PASSED  
         sts_serial|   7|    100000|     100|0.04661608|  PASSED  
         sts_serial|   7|    100000|     100|0.90747243|  PASSED  
         sts_serial|   8|    100000|     100|0.19517131|  PASSED  
         sts_serial|   8|    100000|     100|0.76979629|  PASSED  
         sts_serial|   9|    100000|     100|0.17477898|  PASSED  
         sts_serial|   9|    100000|     100|0.91722005|  PASSED  
         sts_serial|  10|    100000|     100|0.78098352|  PASSED  
         sts_serial|  10|    100000|     100|0.86615492|  PASSED  
         sts_serial|  11|    100000|     100|0.64873253|  PASSED  
         sts_serial|  11|    100000|     100|0.57981945|  PASSED  
         sts_serial|  12|    100000|     100|0.47634540|  PASSED  
         sts_serial|  12|    100000|     100|0.18449207|  PASSED  
         sts_serial|  13|    100000|     100|0.75645866|  PASSED  
         sts_serial|  13|    100000|     100|0.03539615|  PASSED  
         sts_serial|  14|    100000|     100|0.86965703|  PASSED  
         sts_serial|  14|    100000|     100|0.64070570|  PASSED  
         sts_serial|  15|    100000|     100|0.86951991|  PASSED  
         sts_serial|  15|    100000|     100|0.81943081|  PASSED  
         sts_serial|  16|    100000|     100|0.57088163|  PASSED  
         sts_serial|  16|    100000|     100|0.29040060|  PASSED  
        rgb_bitdist|   1|    100000|     100|0.86873833|  PASSED              ]
        rgb_bitdist|   2|    100000|     100|0.85325236|  PASSED              ]
        rgb_bitdist|   3|    100000|     100|0.95226081|  PASSED              ]
        rgb_bitdist|   4|    100000|     100|0.66038635|  PASSED              ]
        rgb_bitdist|   5|    100000|     100|0.13784122|  PASSED              ]
        rgb_bitdist|   6|    100000|     100|0.27142406|  PASSED              ]
        rgb_bitdist|   7|    100000|     100|0.61172905|  PASSED              ]
        rgb_bitdist|   8|    100000|     100|0.39661910|  PASSED              ]
        rgb_bitdist|   9|    100000|     100|0.45469854|  PASSED              ]
        rgb_bitdist|  10|    100000|     100|0.91797334|  PASSED   &lt;=&gt;        ]
        rgb_bitdist|  11|    100000|     100|0.98811206|  PASSED              ]
        rgb_bitdist|  12|    100000|     100|0.24174300|  PASSED              ]
rgb_minimum_distance|   2|     10000|    1000|0.53009831|  PASSED              ]
rgb_minimum_distance|   3|     10000|    1000|0.99123568|  PASSED  &gt;           ]
rgb_minimum_distance|   4|     10000|    1000|0.05278055|  PASSED           &lt;=&gt;]
rgb_minimum_distance|   5|     10000|    1000|0.00192692|   WEAK               ]
   rgb_permutations|   2|    100000|     100|0.25534804|  PASSED              ]
   rgb_permutations|   3|    100000|     100|0.95871871|  PASSED              ]
   rgb_permutations|   4|    100000|     100|0.69024074|  PASSED              ]
   rgb_permutations|   5|    100000|     100|0.62811376|  PASSED              ]
     rgb_lagged_sum|   0|   1000000|     100|0.43118771|  PASSED              ]
     rgb_lagged_sum|   1|   1000000|     100|0.78947942|  PASSED              ]
     rgb_lagged_sum|   2|   1000000|     100|0.54082929|  PASSED              ]
     rgb_lagged_sum|   3|   1000000|     100|0.89304502|  PASSED              ]
     rgb_lagged_sum|   4|   1000000|     100|0.54922923|  PASSED              ]
     rgb_lagged_sum|   5|   1000000|     100|0.52252702|  PASSED   &lt;=&gt;        ]
     rgb_lagged_sum|   6|   1000000|     100|0.50123263|  PASSED              ]
     rgb_lagged_sum|   7|   1000000|     100|0.95607041|  PASSED              ]
     rgb_lagged_sum|   8|   1000000|     100|0.78358255|  PASSED              ]
     rgb_lagged_sum|   9|   1000000|     100|0.93639924|  PASSED        &lt;=&gt;   ]
     rgb_lagged_sum|  10|   1000000|     100|0.96720351|  PASSED              ]
     rgb_lagged_sum|  11|   1000000|     100|0.76648842|  PASSED              ]
     rgb_lagged_sum|  12|   1000000|     100|0.95844403|  PASSED  &lt;=&gt;         ]
     rgb_lagged_sum|  13|   1000000|     100|0.99628444|   WEAK               ]
     rgb_lagged_sum|  14|   1000000|     100|0.17004949|  PASSED         &lt;=&gt;  ]
     rgb_lagged_sum|  15|   1000000|     100|0.78382985|  PASSED              ]
     rgb_lagged_sum|  16|   1000000|     100|0.07884512|  PASSED           &lt;=&gt;]
     rgb_lagged_sum|  17|   1000000|     100|0.23564181|  PASSED              ]
     rgb_lagged_sum|  18|   1000000|     100|0.99832213|   WEAK               ]
     rgb_lagged_sum|  19|   1000000|     100|0.08803558|  PASSED              ]
     rgb_lagged_sum|  20|   1000000|     100|0.92950233|  PASSED              ]
     rgb_lagged_sum|  21|   1000000|     100|0.21138751|  PASSED  &lt;=&gt;         ]
     rgb_lagged_sum|  22|   1000000|     100|0.33451827|  PASSED              ]
     rgb_lagged_sum|  23|   1000000|     100|0.80858319|  PASSED              ]
     rgb_lagged_sum|  24|   1000000|     100|0.51121780|  PASSED              ]
     rgb_lagged_sum|  25|   1000000|     100|0.53501596|  PASSED  &gt;           ]
     rgb_lagged_sum|  26|   1000000|     100|0.10784878|  PASSED     &lt;=&gt;      ]
     rgb_lagged_sum|  27|   1000000|     100|0.83026194|  PASSED              ]
     rgb_lagged_sum|  28|   1000000|     100|0.67926963|  PASSED              ]
     rgb_lagged_sum|  29|   1000000|     100|0.90806411|  PASSED              ]
     rgb_lagged_sum|  30|   1000000|     100|0.98452920|  PASSED              ]
     rgb_lagged_sum|  31|   1000000|     100|0.51741868|  PASSED              ]
     rgb_lagged_sum|  32|   1000000|     100|0.79835395|  PASSED              ]
    rgb_kstest_test|   0|     10000|    1000|0.01515269|  PASSED  
    dab_bytedistrib|   0|  51200000|       1|0.33023025|  PASSED              ]
            dab_dct| 256|     50000|       1|0.08974740|  PASSED              ]
Preparing to run test 207.  ntuple = 0
       dab_filltree|  32|  15000000|       1|0.28064178|  PASSED              ]
       dab_filltree|  32|  15000000|       1|0.85469896|  PASSED  
Preparing to run test 208.  ntuple = 0
      dab_filltree2|   0|   5000000|       1|0.09419009|  PASSED              ]
      dab_filltree2|   1|   5000000|       1|0.02769773|  PASSED  
Preparing to run test 209.  ntuple = 0
       dab_monobit2|  12|  65000000|       1|0.30580656|  PASSED              ]
229GiB 0:37:04 [ 105MiB/s] [                       &lt;=&gt;                        ]

這花了 37 分鐘。注意 3.23e+07 rands /second 的生成速率。rand 是一個 4 字節的字,因此測試以 129 MB/s 的速度執行了 37 分鐘。最後一行顯示了 229GiB 的總字節消耗,這是一個令人驚訝的246GB。將此與問題中使用的 160Mb 進行比較。

從列表中看不出,頑固的頑固測試本身消耗了大約 5GB的隨機性。最初的頑固測試只需要 10MB。

考慮到關於倒帶影響的警告,這就提出了一個問題,即對不到 250GB 的任何東西進行更頑固的測試是否完全可靠。除了“典型模擬應用程序中的現代隨機數生成器很容易需要生成 10^18 或更多隨機數”之外,Robert Brown 一定對推薦的樣本量有所了解。看到我們對 ent 和 diehard 的祖先 diehard 的推薦會很有用。

進一步的暗示是,頑固分子不是 DIY 熵者的首選測試。這個網站上有許多 DIY TRNG,使用從輻射到未初始化 RAM 狀態再到二極體和網路攝像頭的所有東西。頑固分子看似模糊(但很大)的樣本量要求使其無法用於可靠地測試這些設計。

引用自:https://crypto.stackexchange.com/questions/61293