代码之家  ›  专栏  ›  技术社区  ›  dommer

Delphi有密码安全的prng库吗?[关闭]

  •  9
  • dommer  · 技术社区  · 16 年前

    有人能为Delphi(Win32)推荐一个加密安全的伪随机数生成器库吗?

    可以是免费的,也可以是商业的,但理想情况下是一个活跃的项目。我希望它包括源代码。

    6 回复  |  直到 12 年前
        1
  •  8
  •   vcldeveloper    16 年前

    您可以使用Windows CryptoAPI:

    uses Wcrypt2;
    
    function GenerateRandom(Len: Cardinal): TBytes;
    var
      hProv : HCRYPTPROV;
    begin
      if not CryptAcquireContext(@hProv,
                                 nil,
                                 MS_ENHANCED_PROV,
                                 PROV_RSA_FULL,
                                 CRYPT_VERIFYCONTEXT) then
        CryptAcquireContext(@hProv,
                            nil,
                            MS_ENHANCED_PROV,
                            PROV_RSA_FULL,
                            CRYPT_NEWKEYSET + CRYPT_VERIFYCONTEXT);
    
      if hProv > 0 then
      try
        SetLength(Result,Len);
        CryptGenRandom(hProv,Len,@Result[0]);
      finally
        CryptReleaseContext(hProv,0);
      end;
    end;
    

    使用上述代码的示例:

    function BytesToHex(const Bytes: TBytes): string;
    var
      i : integer;
    begin
      for i := 0 to Length(Bytes)-1 do
        Result := Result + IntToHex(Bytes[i],2);
    end;
    
    procedure TForm1.Button1Click(Sender: TObject);
    begin
      ShowMessage(BytesToHex(GenerateRandom(16)));
    end;
    
        2
  •  5
  •   Leo user370469    16 年前

    这个 Delphi Encryption Compendium (在讲德语的Delphi社区中是有名的ish,但是没有其他地方——大概是因为它没有被正式提升)包含密码安全 Yarrow RNG .

    包括这个单位 DECRandom (也许 DECUtils )像这样使用它(这个例子使用 IInteger 但这不是强制性的):

    function generateRandomNumber: IInteger; 
    var 
      A: IInteger;  
    begin 
      NRnd(A, 512);  // generate 512 Bit random number, 2^512 <= A < 2^513 
      Result := A;
    end; 
    
    initialization 
      // Method 1: uses system timer to initialize the RNG (seed)
      RandomSeed;   
      // Method 2: use own seed
      randomSeed(Data, SizeOf(Data));
    
        3
  •  2
  •   gammatester    12 年前

    查看isaac(间接、移位、累积、添加和计数),一个快速的prng,也是加密安全的(burtleburtle.net/bob/rand/isaacafa.html)。也许艾萨克和著名的梅森龙卷风一样快。

    Wolfgang Ehrhardt已经为Isaac完成了Pascal/Delphi端口,可在 http://www.wolfgang-ehrhardt.de/misc_en.html#prng (免费提供资源)。还有一个链接指向作者网站上提供的另一个Delphi端口,但我将使用“Wolfgang Ehrhardt”版本。我知道他的网站( http://www.wolfgang-ehrhardt.de/index.html )多年来,他一直在更新帕斯卡/德尔菲的例行程序,从那时起。当然应该是这方面的专家!

        4
  •  1
  •   Alex K.    16 年前

    您可以使用现有的win32 CryptGenRandom() 应用程序编程接口。

        5
  •  0
  •   Mark Wilkins    16 年前

    OpenSSL是一种可能性。虽然我不知道Delphi版本是否可用,但源代码是可用的。它包括一个 cryptographically secure prng . 这是一个活跃的项目,但对于你正在寻找的东西来说,它可能是多余的。

        6
  •  0
  •   shunty    16 年前

    我还打算建议 OpenSSL libraries . 您还可以获得加密、SSL、哈希等功能。
    Indy已经转换了很多头文件,并包含了rand_屏幕——但显然,在没有用户界面的程序上,这是不可以/不应该使用的。不幸的是,它漏掉了大部分的兰德公司的产品——但它们很容易进口和使用。
    如:

    function RAND_load_file(const filename: PAnsiChar; max_bytes: longint): integer; cdecl; external 'libeay32.dll';
    function RAND_bytes(buf: PByte; num: integer): integer; cdecl; external 'libeay32.dll';
    function RAND_pseudo_bytes(buf: PByte; num: integer): integer; cdecl; external 'libeay32.dll';
    

    然后在代码中:

      RAND_load_file(PAnsiChar(AnsiString('name-of-seed-file')), 512);
      //or
      //RAND_screen;
      ...
      ...
      const
        PKCS5_SALT_LEN = 8;
      var
        salt: TBytes;
      begin
        SetLength(salt, PKCS5_SALT_LEN);
        RAND_pseudo_bytes(@salt[0], PKCS5_SALT_LEN);
        ...
      end;
    

    当然,同样的种子问题仍然适用。

    推荐文章