Browse Source

Merge branch 'master' into travis

Ugochukwu Mmaduekwe 6 years ago
parent
commit
1e151eedf4
98 changed files with 6061 additions and 788 deletions
  1. 9 1
      CryptoLib.Samples/Delphi.Samples/UsageSamples.dpr
  2. 21 2
      CryptoLib.Tests/Delphi.Tests/CryptoLib.Tests.TestInsight.dpr
  3. 21 2
      CryptoLib.Tests/Delphi.Tests/CryptoLib.Tests.dpr
  4. 49 1
      CryptoLib.Tests/FreePascal.Tests/CryptoLib.Tests.lpi
  5. 12 1
      CryptoLib.Tests/FreePascal.Tests/CryptoLib.lpr
  6. 45 1
      CryptoLib.Tests/FreePascal.Tests/CryptoLibConsole.Tests.lpi
  7. 12 1
      CryptoLib.Tests/FreePascal.Tests/CryptoLibConsole.lpr
  8. 297 0
      CryptoLib.Tests/src/Crypto/Argon2Tests.pas
  9. 4 4
      CryptoLib.Tests/src/Crypto/DSATests.pas
  10. 24 0
      CryptoLib.Tests/src/Crypto/HMacTests.pas
  11. 174 0
      CryptoLib.Tests/src/Crypto/Kdf1GeneratorTests.pas
  12. 194 0
      CryptoLib.Tests/src/Crypto/Kdf2GeneratorTests.pas
  13. 1 1
      CryptoLib.Tests/src/Crypto/PaddingTests.pas
  14. 28 1
      CryptoLib.Tests/src/Crypto/Pkcs5Tests.pas
  15. 250 0
      CryptoLib.Tests/src/Crypto/ScryptTests.pas
  16. 39 0
      CryptoLib.Tests/src/Math/BigIntegerTests.pas
  17. 2 2
      CryptoLib.Tests/src/Math/ECPointTests.pas
  18. 6 4
      CryptoLib.Tests/src/Math/PascalCoinECIESTests.pas
  19. 304 0
      CryptoLib.Tests/src/Others/DigestTests.pas
  20. 429 0
      CryptoLib.Tests/src/Others/Ed25519HigherLevelTests.pas
  21. 66 60
      CryptoLib.Tests/src/Others/NamedCurveTests.pas
  22. 171 0
      CryptoLib.Tests/src/Others/ShortenedDigestTests.pas
  23. 23 1
      CryptoLib.Tests/src/Others/SignerUtilitiesTests.pas
  24. 136 0
      CryptoLib.Tests/src/Others/X25519HigherLevelTests.pas
  25. 280 0
      CryptoLib.Tests/src/Security/DigestUtilitiesTests.pas
  26. 39 0
      CryptoLib.Tests/src/Utils/ClpIShortenedDigest.pas
  27. 176 0
      CryptoLib.Tests/src/Utils/ClpShortenedDigest.pas
  28. 4 4
      CryptoLib/src/Asn1/ClpAsn1Objects.pas
  29. 2 0
      CryptoLib/src/Asn1/Edec/ClpEdECObjectIdentifiers.pas
  30. 12 1
      CryptoLib/src/Asn1/Misc/ClpMiscObjectIdentifiers.pas
  31. 25 10
      CryptoLib/src/Asn1/Nist/ClpNistObjectIdentifiers.pas
  32. 16 2
      CryptoLib/src/Asn1/Pkcs/ClpPkcsObjectIdentifiers.pas
  33. 0 1
      CryptoLib/src/Asn1/Sec/ClpSecNamedCurves.pas
  34. 968 0
      CryptoLib/src/Asn1/TeleTrust/ClpTeleTrusTNamedCurves.pas
  35. 177 1
      CryptoLib/src/Asn1/TeleTrust/ClpTeleTrusTObjectIdentifiers.pas
  36. 17 49
      CryptoLib/src/Asn1/X9/ClpECNamedCurveTable.pas
  37. 1 1
      CryptoLib/src/Crypto/ClpBufferedBlockCipher.pas
  38. 44 5
      CryptoLib/src/Crypto/Digests/ClpDigest.pas
  39. 4 0
      CryptoLib/src/Crypto/Engines/ClpAesEngine.pas
  40. 4 0
      CryptoLib/src/Crypto/Engines/ClpAesLightEngine.pas
  41. 4 0
      CryptoLib/src/Crypto/Engines/ClpBlowfishEngine.pas
  42. 6 0
      CryptoLib/src/Crypto/Engines/ClpChaChaEngine.pas
  43. 3 3
      CryptoLib/src/Crypto/Engines/ClpIESEngine.pas
  44. 1 1
      CryptoLib/src/Crypto/Engines/ClpPascalCoinIESEngine.pas
  45. 5 1
      CryptoLib/src/Crypto/Engines/ClpRijndaelEngine.pas
  46. 11 0
      CryptoLib/src/Crypto/Engines/ClpSalsa20Engine.pas
  47. 48 27
      CryptoLib/src/Crypto/Engines/ClpSpeckEngine.pas
  48. 53 26
      CryptoLib/src/Crypto/Engines/ClpSpeckLegacyEngine.pas
  49. 6 0
      CryptoLib/src/Crypto/Engines/ClpXSalsa20Engine.pas
  50. 265 0
      CryptoLib/src/Crypto/Generators/ClpArgon2ParametersGenerator.pas
  51. 63 0
      CryptoLib/src/Crypto/Generators/ClpKdf1BytesGenerator.pas
  52. 2 83
      CryptoLib/src/Crypto/Generators/ClpPbeParametersGenerator.pas
  53. 28 5
      CryptoLib/src/Crypto/Generators/ClpPkcs5S2ParametersGenerator.pas
  54. 199 0
      CryptoLib/src/Crypto/Generators/ClpScryptParametersGenerator.pas
  55. 15 0
      CryptoLib/src/Crypto/Macs/ClpHMac.pas
  56. 2 2
      CryptoLib/src/Crypto/Modes/ClpBlockCipherModes.pas
  57. 0 1
      CryptoLib/src/Crypto/Paddings/ClpPaddedBufferedBlockCipher.pas
  58. 0 17
      CryptoLib/src/Crypto/Paddings/ClpPaddingModes.pas
  59. 1 5
      CryptoLib/src/Crypto/Parameters/ClpHkdfParameters.pas
  60. 7 1
      CryptoLib/src/Crypto/Parameters/ClpKeyParameter.pas
  61. 7 1
      CryptoLib/src/Crypto/Parameters/ClpParametersWithIV.pas
  62. 1 1
      CryptoLib/src/Crypto/Prng/ClpDigestRandomGenerator.pas
  63. 0 1
      CryptoLib/src/Crypto/Signers/ClpECNRSigner.pas
  64. 5 0
      CryptoLib/src/Crypto/Signers/ClpEd25519Blake2BSigner.pas
  65. 5 0
      CryptoLib/src/Crypto/Signers/ClpEd25519CtxBlake2BSigner.pas
  66. 5 0
      CryptoLib/src/Crypto/Signers/ClpEd25519CtxSigner.pas
  67. 5 0
      CryptoLib/src/Crypto/Signers/ClpEd25519PhBlake2BSigner.pas
  68. 5 0
      CryptoLib/src/Crypto/Signers/ClpEd25519PhSigner.pas
  69. 5 0
      CryptoLib/src/Crypto/Signers/ClpEd25519Signer.pas
  70. 1 1
      CryptoLib/src/Crypto/Signers/ClpHMacDsaKCalculator.pas
  71. 1 1
      CryptoLib/src/Crypto/Signers/SignersEncodings/ClpSignersEncodings.pas
  72. 50 0
      CryptoLib/src/Interfaces/ClpIArgon2ParametersGenerator.pas
  73. 2 2
      CryptoLib/src/Interfaces/ClpIAsn1Objects.pas
  74. 6 3
      CryptoLib/src/Interfaces/ClpIDigest.pas
  75. 1 1
      CryptoLib/src/Interfaces/ClpIECC.pas
  76. 36 0
      CryptoLib/src/Interfaces/ClpIKdf1BytesGenerator.pas
  77. 1 0
      CryptoLib/src/Interfaces/ClpIKeyParameter.pas
  78. 2 0
      CryptoLib/src/Interfaces/ClpIMac.pas
  79. 1 0
      CryptoLib/src/Interfaces/ClpIParametersWithIV.pas
  80. 1 32
      CryptoLib/src/Interfaces/ClpIPbeParametersGenerator.pas
  81. 5 1
      CryptoLib/src/Interfaces/ClpIPkcs5S2ParametersGenerator.pas
  82. 40 0
      CryptoLib/src/Interfaces/ClpIScryptParametersGenerator.pas
  83. 20 1
      CryptoLib/src/Math/ClpBigInteger.pas
  84. 0 95
      CryptoLib/src/Math/EC/ClpValidityPrecompInfo.pas
  85. 19 0
      CryptoLib/src/Math/EC/Rfc7748/ClpX25519.pas
  86. 378 0
      CryptoLib/src/Packages/Delphi/CryptoLib4PascalPackage.dpk
  87. 272 244
      CryptoLib/src/Packages/FPC/CryptoLib4PascalPackage.lpk
  88. 16 14
      CryptoLib/src/Packages/FPC/CryptoLib4PascalPackage.pas
  89. 171 0
      CryptoLib/src/Security/ClpAgreementUtilities.pas
  90. 1 1
      CryptoLib/src/Security/ClpCipherUtilities.pas
  91. 56 36
      CryptoLib/src/Security/ClpDigestUtilities.pas
  92. 13 5
      CryptoLib/src/Security/ClpGeneratorUtilities.pas
  93. 1 1
      CryptoLib/src/Security/ClpMacUtilities.pas
  94. 4 1
      CryptoLib/src/Security/ClpParameterUtilities.pas
  95. 69 0
      CryptoLib/src/Security/ClpSignerUtilities.pas
  96. 46 10
      CryptoLib/src/Utils/ClpArrayUtils.pas
  97. 0 2
      CryptoLib/src/Utils/ClpCryptoLibTypes.pas
  98. 5 6
      CryptoLib/src/Utils/Randoms/ClpPcgRandomMinimal.pas

+ 9 - 1
CryptoLib.Samples/Delphi.Samples/UsageSamples.dpr

@@ -222,7 +222,7 @@ uses
   ClpIHkdfParameters in '..\..\CryptoLib\src\Interfaces\ClpIHkdfParameters.pas',
   ClpDsaParameterGenerationParameters in '..\..\CryptoLib\src\Crypto\Parameters\ClpDsaParameterGenerationParameters.pas',
   ClpIDsaParameterGenerationParameters in '..\..\CryptoLib\src\Interfaces\ClpIDsaParameterGenerationParameters.pas',
-  ClpValidityPrecompInfo in '..\..\CryptoLib\src\Math\EC\ClpValidityPrecompInfo.pas',
+  ClpValidityPrecompInfo in '..\..\CryptoLib\src\Math\EC\Multiplier\ClpValidityPrecompInfo.pas',
   ClpIValidityPrecompInfo in '..\..\CryptoLib\src\Interfaces\ClpIValidityPrecompInfo.pas',
   ClpDsaParametersGenerator in '..\..\CryptoLib\src\Crypto\Generators\ClpDsaParametersGenerator.pas',
   ClpIDsaParametersGenerator in '..\..\CryptoLib\src\Interfaces\ClpIDsaParametersGenerator.pas',
@@ -337,6 +337,14 @@ uses
   ClpIEd25519PhBlake2BSigner in '..\..\CryptoLib\src\Interfaces\ClpIEd25519PhBlake2BSigner.pas',
   ClpEd25519PhSigner in '..\..\CryptoLib\src\Crypto\Signers\ClpEd25519PhSigner.pas',
   ClpEd25519PhBlake2BSigner in '..\..\CryptoLib\src\Crypto\Signers\ClpEd25519PhBlake2BSigner.pas',
+  ClpTeleTrusTNamedCurves in '..\..\CryptoLib\src\Asn1\TeleTrust\ClpTeleTrusTNamedCurves.pas',
+  ClpAgreementUtilities in '..\..\CryptoLib\src\Security\ClpAgreementUtilities.pas',
+  ClpKdf1BytesGenerator in '..\..\CryptoLib\src\Crypto\Generators\ClpKdf1BytesGenerator.pas',
+  ClpIKdf1BytesGenerator in '..\..\CryptoLib\src\Interfaces\ClpIKdf1BytesGenerator.pas',
+  ClpIArgon2ParametersGenerator in '..\..\CryptoLib\src\Interfaces\ClpIArgon2ParametersGenerator.pas',
+  ClpArgon2ParametersGenerator in '..\..\CryptoLib\src\Crypto\Generators\ClpArgon2ParametersGenerator.pas',
+  ClpScryptParametersGenerator in '..\..\CryptoLib\src\Crypto\Generators\ClpScryptParametersGenerator.pas',
+  ClpIScryptParametersGenerator in '..\..\CryptoLib\src\Interfaces\ClpIScryptParametersGenerator.pas',
   UsageExamples in '..\src\UsageExamples.pas';
 
 begin

+ 21 - 2
CryptoLib.Tests/Delphi.Tests/CryptoLib.Tests.TestInsight.dpr

@@ -232,7 +232,7 @@ uses
   ClpIHkdfParameters in '..\..\CryptoLib\src\Interfaces\ClpIHkdfParameters.pas',
   ClpDsaParameterGenerationParameters in '..\..\CryptoLib\src\Crypto\Parameters\ClpDsaParameterGenerationParameters.pas',
   ClpIDsaParameterGenerationParameters in '..\..\CryptoLib\src\Interfaces\ClpIDsaParameterGenerationParameters.pas',
-  ClpValidityPrecompInfo in '..\..\CryptoLib\src\Math\EC\ClpValidityPrecompInfo.pas',
+  ClpValidityPrecompInfo in '..\..\CryptoLib\src\Math\EC\Multiplier\ClpValidityPrecompInfo.pas',
   ClpIValidityPrecompInfo in '..\..\CryptoLib\src\Interfaces\ClpIValidityPrecompInfo.pas',
   ClpDsaParametersGenerator in '..\..\CryptoLib\src\Crypto\Generators\ClpDsaParametersGenerator.pas',
   ClpIDsaParametersGenerator in '..\..\CryptoLib\src\Interfaces\ClpIDsaParametersGenerator.pas',
@@ -347,8 +347,18 @@ uses
   ClpIEd25519PhBlake2BSigner in '..\..\CryptoLib\src\Interfaces\ClpIEd25519PhBlake2BSigner.pas',
   ClpEd25519PhSigner in '..\..\CryptoLib\src\Crypto\Signers\ClpEd25519PhSigner.pas',
   ClpEd25519PhBlake2BSigner in '..\..\CryptoLib\src\Crypto\Signers\ClpEd25519PhBlake2BSigner.pas',
+  ClpTeleTrusTNamedCurves in '..\..\CryptoLib\src\Asn1\TeleTrust\ClpTeleTrusTNamedCurves.pas',
+  ClpAgreementUtilities in '..\..\CryptoLib\src\Security\ClpAgreementUtilities.pas',
+  ClpKdf1BytesGenerator in '..\..\CryptoLib\src\Crypto\Generators\ClpKdf1BytesGenerator.pas',
+  ClpIKdf1BytesGenerator in '..\..\CryptoLib\src\Interfaces\ClpIKdf1BytesGenerator.pas',
+  ClpIArgon2ParametersGenerator in '..\..\CryptoLib\src\Interfaces\ClpIArgon2ParametersGenerator.pas',
+  ClpArgon2ParametersGenerator in '..\..\CryptoLib\src\Crypto\Generators\ClpArgon2ParametersGenerator.pas',
+  ClpScryptParametersGenerator in '..\..\CryptoLib\src\Crypto\Generators\ClpScryptParametersGenerator.pas',
+  ClpIScryptParametersGenerator in '..\..\CryptoLib\src\Interfaces\ClpIScryptParametersGenerator.pas',
   ClpFixedSecureRandom in '..\src\Utils\ClpFixedSecureRandom.pas',
   ClpIFixedSecureRandom in '..\src\Utils\ClpIFixedSecureRandom.pas',
+  ClpIShortenedDigest in '..\src\Utils\ClpIShortenedDigest.pas',
+  ClpShortenedDigest in '..\src\Utils\ClpShortenedDigest.pas',
   BlowfishTestVectors in '..\src\Crypto\BlowfishTestVectors.pas',
   BlockCipherVectorTests in '..\src\Crypto\BlockCipherVectorTests.pas',
   AESTestVectors in '..\src\Crypto\AESTestVectors.pas',
@@ -404,7 +414,16 @@ uses
   CTSTests in '..\src\Crypto\CTSTests.pas',
   PascalCoinECIESTests in '..\src\Math\PascalCoinECIESTests.pas',
   X25519Tests in '..\src\Math\EC\Rfc7748\X25519Tests.pas',
-  Ed25519Tests in '..\src\Math\EC\Rfc8032\Ed25519Tests.pas';
+  Ed25519Tests in '..\src\Math\EC\Rfc8032\Ed25519Tests.pas',
+  X25519HigherLevelTests in '..\src\Others\X25519HigherLevelTests.pas',
+  Ed25519HigherLevelTests in '..\src\Others\Ed25519HigherLevelTests.pas',
+  ShortenedDigestTests in '..\src\Others\ShortenedDigestTests.pas',
+  Kdf1GeneratorTests in '..\src\Crypto\Kdf1GeneratorTests.pas',
+  Kdf2GeneratorTests in '..\src\Crypto\Kdf2GeneratorTests.pas',
+  Argon2Tests in '..\src\Crypto\Argon2Tests.pas',
+  DigestUtilitiesTests in '..\src\Security\DigestUtilitiesTests.pas',
+  DigestTests in '..\src\Others\DigestTests.pas',
+  ScryptTests in '..\src\Crypto\ScryptTests.pas';
 
 begin
 

+ 21 - 2
CryptoLib.Tests/Delphi.Tests/CryptoLib.Tests.dpr

@@ -235,7 +235,7 @@ uses
   ClpIHkdfParameters in '..\..\CryptoLib\src\Interfaces\ClpIHkdfParameters.pas',
   ClpDsaParameterGenerationParameters in '..\..\CryptoLib\src\Crypto\Parameters\ClpDsaParameterGenerationParameters.pas',
   ClpIDsaParameterGenerationParameters in '..\..\CryptoLib\src\Interfaces\ClpIDsaParameterGenerationParameters.pas',
-  ClpValidityPrecompInfo in '..\..\CryptoLib\src\Math\EC\ClpValidityPrecompInfo.pas',
+  ClpValidityPrecompInfo in '..\..\CryptoLib\src\Math\EC\Multiplier\ClpValidityPrecompInfo.pas',
   ClpIValidityPrecompInfo in '..\..\CryptoLib\src\Interfaces\ClpIValidityPrecompInfo.pas',
   ClpDsaParametersGenerator in '..\..\CryptoLib\src\Crypto\Generators\ClpDsaParametersGenerator.pas',
   ClpIDsaParametersGenerator in '..\..\CryptoLib\src\Interfaces\ClpIDsaParametersGenerator.pas',
@@ -350,8 +350,18 @@ uses
   ClpIEd25519PhBlake2BSigner in '..\..\CryptoLib\src\Interfaces\ClpIEd25519PhBlake2BSigner.pas',
   ClpEd25519PhSigner in '..\..\CryptoLib\src\Crypto\Signers\ClpEd25519PhSigner.pas',
   ClpEd25519PhBlake2BSigner in '..\..\CryptoLib\src\Crypto\Signers\ClpEd25519PhBlake2BSigner.pas',
+  ClpTeleTrusTNamedCurves in '..\..\CryptoLib\src\Asn1\TeleTrust\ClpTeleTrusTNamedCurves.pas',
+  ClpAgreementUtilities in '..\..\CryptoLib\src\Security\ClpAgreementUtilities.pas',
+  ClpKdf1BytesGenerator in '..\..\CryptoLib\src\Crypto\Generators\ClpKdf1BytesGenerator.pas',
+  ClpIKdf1BytesGenerator in '..\..\CryptoLib\src\Interfaces\ClpIKdf1BytesGenerator.pas',
+  ClpIArgon2ParametersGenerator in '..\..\CryptoLib\src\Interfaces\ClpIArgon2ParametersGenerator.pas',
+  ClpArgon2ParametersGenerator in '..\..\CryptoLib\src\Crypto\Generators\ClpArgon2ParametersGenerator.pas',
+  ClpScryptParametersGenerator in '..\..\CryptoLib\src\Crypto\Generators\ClpScryptParametersGenerator.pas',
+  ClpIScryptParametersGenerator in '..\..\CryptoLib\src\Interfaces\ClpIScryptParametersGenerator.pas',
   ClpFixedSecureRandom in '..\src\Utils\ClpFixedSecureRandom.pas',
   ClpIFixedSecureRandom in '..\src\Utils\ClpIFixedSecureRandom.pas',
+  ClpIShortenedDigest in '..\src\Utils\ClpIShortenedDigest.pas',
+  ClpShortenedDigest in '..\src\Utils\ClpShortenedDigest.pas',
   BlowfishTestVectors in '..\src\Crypto\BlowfishTestVectors.pas',
   BlockCipherVectorTests in '..\src\Crypto\BlockCipherVectorTests.pas',
   AESTestVectors in '..\src\Crypto\AESTestVectors.pas',
@@ -407,7 +417,16 @@ uses
   CTSTests in '..\src\Crypto\CTSTests.pas',
   PascalCoinECIESTests in '..\src\Math\PascalCoinECIESTests.pas',
   X25519Tests in '..\src\Math\EC\Rfc7748\X25519Tests.pas',
-  Ed25519Tests in '..\src\Math\EC\Rfc8032\Ed25519Tests.pas';
+  Ed25519Tests in '..\src\Math\EC\Rfc8032\Ed25519Tests.pas',
+  X25519HigherLevelTests in '..\src\Others\X25519HigherLevelTests.pas',
+  Ed25519HigherLevelTests in '..\src\Others\Ed25519HigherLevelTests.pas',
+  ShortenedDigestTests in '..\src\Others\ShortenedDigestTests.pas',
+  Kdf1GeneratorTests in '..\src\Crypto\Kdf1GeneratorTests.pas',
+  Kdf2GeneratorTests in '..\src\Crypto\Kdf2GeneratorTests.pas',
+  Argon2Tests in '..\src\Crypto\Argon2Tests.pas',
+  DigestUtilitiesTests in '..\src\Security\DigestUtilitiesTests.pas',
+  DigestTests in '..\src\Others\DigestTests.pas',
+  ScryptTests in '..\src\Crypto\ScryptTests.pas';
 
 begin
 

+ 49 - 1
CryptoLib.Tests/FreePascal.Tests/CryptoLib.Tests.lpi

@@ -77,7 +77,7 @@
         <PackageName Value="FCL"/>
       </Item4>
     </RequiredPackages>
-    <Units Count="59">
+    <Units Count="71">
       <Unit0>
         <Filename Value="CryptoLib.lpr"/>
         <IsPartOfProject Value="True"/>
@@ -315,6 +315,54 @@
         <Filename Value="..\src\Math\EC\Rfc8032\Ed25519Tests.pas"/>
         <IsPartOfProject Value="True"/>
       </Unit58>
+      <Unit59>
+        <Filename Value="..\src\Others\Ed25519HigherLevelTests.pas"/>
+        <IsPartOfProject Value="True"/>
+      </Unit59>
+      <Unit60>
+        <Filename Value="..\src\Others\X25519HigherLevelTests.pas"/>
+        <IsPartOfProject Value="True"/>
+      </Unit60>
+      <Unit61>
+        <Filename Value="..\src\Utils\ClpShortenedDigest.pas"/>
+        <IsPartOfProject Value="True"/>
+      </Unit61>
+      <Unit62>
+        <Filename Value="..\src\Utils\ClpIShortenedDigest.pas"/>
+        <IsPartOfProject Value="True"/>
+      </Unit62>
+      <Unit63>
+        <Filename Value="..\src\Others\ShortenedDigestTests.pas"/>
+        <IsPartOfProject Value="True"/>
+      </Unit63>
+      <Unit64>
+        <Filename Value="..\src\Crypto\Kdf2GeneratorTests.pas"/>
+        <IsPartOfProject Value="True"/>
+      </Unit64>
+      <Unit65>
+        <Filename Value="..\src\Crypto\Kdf1GeneratorTests.pas"/>
+        <IsPartOfProject Value="True"/>
+      </Unit65>
+      <Unit66>
+        <Filename Value="..\src\Crypto\Argon2Tests.pas"/>
+        <IsPartOfProject Value="True"/>
+      </Unit66>
+      <Unit67>
+        <Filename Value="..\src\Others\DigestTests.pas"/>
+        <IsPartOfProject Value="True"/>
+      </Unit67>
+      <Unit68>
+        <Filename Value="..\src\Security\DigestUtilitiesTests.pas"/>
+        <IsPartOfProject Value="True"/>
+      </Unit68>
+      <Unit69>
+        <Filename Value="CryptoLib.Tests.lpi"/>
+        <IsPartOfProject Value="True"/>
+      </Unit69>
+      <Unit70>
+        <Filename Value="..\src\Crypto\ScryptTests.pas"/>
+        <IsPartOfProject Value="True"/>
+      </Unit70>
     </Units>
   </ProjectOptions>
   <CompilerOptions>

+ 12 - 1
CryptoLib.Tests/FreePascal.Tests/CryptoLib.lpr

@@ -62,8 +62,19 @@ uses
   CTSTests,
   X25519Tests,
   Ed25519Tests,
+  X25519HigherLevelTests,
+  Ed25519HigherLevelTests,
+  ShortenedDigestTests,
+  Kdf1GeneratorTests,
+  Kdf2GeneratorTests,
+  Argon2Tests,
+  ScryptTests,
+  DigestTests,
+  DigestUtilitiesTests,
   ClpFixedSecureRandom,
-  ClpIFixedSecureRandom;
+  ClpIFixedSecureRandom,
+  ClpShortenedDigest,
+  ClpIShortenedDigest;
 
 {$R *.res}
 

+ 45 - 1
CryptoLib.Tests/FreePascal.Tests/CryptoLibConsole.Tests.lpi

@@ -37,7 +37,7 @@
         <PackageName Value="FCL"/>
       </Item2>
     </RequiredPackages>
-    <Units Count="59">
+    <Units Count="70">
       <Unit0>
         <Filename Value="CryptoLibConsole.lpr"/>
         <IsPartOfProject Value="True"/>
@@ -274,6 +274,50 @@
         <Filename Value="..\src\Math\EC\Rfc8032\Ed25519Tests.pas"/>
         <IsPartOfProject Value="True"/>
       </Unit58>
+      <Unit59>
+        <Filename Value="..\src\Others\Ed25519HigherLevelTests.pas"/>
+        <IsPartOfProject Value="True"/>
+      </Unit59>
+      <Unit60>
+        <Filename Value="..\src\Others\X25519HigherLevelTests.pas"/>
+        <IsPartOfProject Value="True"/>
+      </Unit60>
+      <Unit61>
+        <Filename Value="..\src\Utils\ClpShortenedDigest.pas"/>
+        <IsPartOfProject Value="True"/>
+      </Unit61>
+      <Unit62>
+        <Filename Value="..\src\Utils\ClpIShortenedDigest.pas"/>
+        <IsPartOfProject Value="True"/>
+      </Unit62>
+      <Unit63>
+        <Filename Value="..\src\Others\ShortenedDigestTests.pas"/>
+        <IsPartOfProject Value="True"/>
+      </Unit63>
+      <Unit64>
+        <Filename Value="..\src\Crypto\Kdf1GeneratorTests.pas"/>
+        <IsPartOfProject Value="True"/>
+      </Unit64>
+      <Unit65>
+        <Filename Value="..\src\Crypto\Kdf2GeneratorTests.pas"/>
+        <IsPartOfProject Value="True"/>
+      </Unit65>
+      <Unit66>
+        <Filename Value="..\src\Crypto\Argon2Tests.pas"/>
+        <IsPartOfProject Value="True"/>
+      </Unit66>
+      <Unit67>
+        <Filename Value="..\src\Others\DigestTests.pas"/>
+        <IsPartOfProject Value="True"/>
+      </Unit67>
+      <Unit68>
+        <Filename Value="..\src\Security\DigestUtilitiesTests.pas"/>
+        <IsPartOfProject Value="True"/>
+      </Unit68>
+      <Unit69>
+        <Filename Value="..\src\Crypto\ScryptTests.pas"/>
+        <IsPartOfProject Value="True"/>
+      </Unit69>
     </Units>
   </ProjectOptions>
   <CompilerOptions>

+ 12 - 1
CryptoLib.Tests/FreePascal.Tests/CryptoLibConsole.lpr

@@ -60,8 +60,19 @@ uses
   CTSTests,
   X25519Tests,
   Ed25519Tests,
+  X25519HigherLevelTests,
+  Ed25519HigherLevelTests,
+  ShortenedDigestTests,
+  Kdf1GeneratorTests,
+  Kdf2GeneratorTests,
+  Argon2Tests,
+  ScryptTests,
+  DigestTests,
+  DigestUtilitiesTests,
   ClpFixedSecureRandom,
-  ClpIFixedSecureRandom;
+  ClpIFixedSecureRandom,
+  ClpShortenedDigest,
+  ClpIShortenedDigest;
 
 type
 

+ 297 - 0
CryptoLib.Tests/src/Crypto/Argon2Tests.pas

@@ -0,0 +1,297 @@
+{ *********************************************************************************** }
+{ *                              CryptoLib Library                                  * }
+{ *                Copyright (c) 2018 - 20XX Ugochukwu Mmaduekwe                    * }
+{ *                 Github Repository <https://github.com/Xor-el>                   * }
+
+{ *  Distributed under the MIT software license, see the accompanying file LICENSE  * }
+{ *          or visit http://www.opensource.org/licenses/mit-license.php.           * }
+
+{ *                              Acknowledgements:                                  * }
+{ *                                                                                 * }
+{ *      Thanks to Sphere 10 Software (http://www.sphere10.com/) for sponsoring     * }
+{ *                           development of this library                           * }
+
+{ * ******************************************************************************* * }
+
+(* &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&& *)
+
+unit Argon2Tests;
+
+interface
+
+{$IFDEF FPC}
+{$MODE DELPHI}
+{$ENDIF FPC}
+
+uses
+  SysUtils,
+{$IFDEF FPC}
+  fpcunit,
+  testregistry,
+{$ELSE}
+  TestFramework,
+{$ENDIF FPC}
+  ClpIKeyParameter,
+  ClpArgon2ParametersGenerator,
+  ClpIArgon2ParametersGenerator,
+  ClpConverters;
+
+type
+
+  TCryptoLibTestCase = class abstract(TTestCase)
+
+  end;
+
+type
+
+  /// <summary>
+  /// A test class for Argon2.
+  /// </summary>
+  TTestArgon2 = class(TCryptoLibTestCase)
+
+  private
+
+    const
+    // multiplied by 8 to get it in bits
+    DEFAULT_OUTPUTLEN_IN_BITS = Int32(32 * 8);
+
+    procedure HashTestFromInternetDraft(AArgon2Type: TArgon2Type;
+      AArgon2Version: TArgon2Version; AIterations, AMemoryAsKB,
+      AParallelism: Int32; const AAdditional, ASecret, ASalt, APassword,
+      APasswordRef: String; AOutputLength: Int32);
+
+    procedure HashTestOthers(AArgon2Type: TArgon2Type;
+      AArgon2Version: TArgon2Version; AIterations, AMemory, AParallelism: Int32;
+      const APassword, ASalt, APasswordRef: String; AOutputLength: Int32);
+
+  protected
+
+    procedure SetUp; override;
+    procedure TearDown; override;
+  published
+
+    procedure TestVectorsFromInternetDraft;
+    procedure TestOthers;
+
+  end;
+
+implementation
+
+{ TTestArgon2 }
+
+procedure TTestArgon2.HashTestFromInternetDraft(AArgon2Type: TArgon2Type;
+  AArgon2Version: TArgon2Version; AIterations, AMemoryAsKB, AParallelism: Int32;
+  const AAdditional, ASecret, ASalt, APassword, APasswordRef: String;
+  AOutputLength: Int32);
+var
+  LArgon2Generator: IArgon2ParametersGenerator;
+  LActual: String;
+  LAdditional, LSecret, LSalt, LPassword: TBytes;
+begin
+
+  LAdditional := TConverters.ConvertHexStringToBytes(AAdditional);
+  LSecret := TConverters.ConvertHexStringToBytes(ASecret);
+  LSalt := TConverters.ConvertHexStringToBytes(ASalt);
+  LPassword := TConverters.ConvertHexStringToBytes(APassword);
+
+  LArgon2Generator := TArgon2ParametersGenerator.Create();
+
+  //
+  // Set the parameters.
+  //
+
+  LArgon2Generator.Init(AArgon2Type, AArgon2Version, LPassword, LSalt, LSecret,
+    LAdditional, AIterations, AMemoryAsKB, AParallelism,
+    TArgon2MemoryCostType.a2mctMemoryAsKB);
+
+  LActual := TConverters.ConvertBytesToHexString
+    ((LArgon2Generator.GenerateDerivedMacParameters(AOutputLength)
+    as IKeyParameter).GetKey(), False);
+
+  LArgon2Generator.Clear();
+
+  CheckEquals(APasswordRef, LActual, Format('Expected %s but got %s.',
+    [APasswordRef, LActual]));
+
+end;
+
+procedure TTestArgon2.HashTestOthers(AArgon2Type: TArgon2Type;
+  AArgon2Version: TArgon2Version; AIterations, AMemory, AParallelism: Int32;
+  const APassword, ASalt, APasswordRef: String; AOutputLength: Int32);
+var
+  LArgon2Generator: IArgon2ParametersGenerator;
+  LSalt, LPassword: TBytes;
+  LActual: String;
+begin
+
+  LSalt := TConverters.ConvertStringToBytes(ASalt, TEncoding.ASCII);
+  LPassword := TConverters.ConvertStringToBytes(APassword, TEncoding.ASCII);
+
+  LArgon2Generator := TArgon2ParametersGenerator.Create();
+
+  //
+  // Set the parameters.
+  //
+
+  LArgon2Generator.Init(AArgon2Type, AArgon2Version, LPassword, LSalt, Nil, Nil,
+    AIterations, AMemory, AParallelism,
+    TArgon2MemoryCostType.a2mctMemoryPowOfTwo);
+
+  LActual := TConverters.ConvertBytesToHexString
+    ((LArgon2Generator.GenerateDerivedMacParameters(AOutputLength)
+    as IKeyParameter).GetKey(), False);
+
+  LArgon2Generator.Clear();
+
+  CheckEquals(APasswordRef, LActual, Format('Expected %s but got %s.',
+    [APasswordRef, LActual]));
+
+end;
+
+procedure TTestArgon2.SetUp;
+begin
+  inherited;
+
+end;
+
+procedure TTestArgon2.TearDown;
+begin
+  inherited;
+
+end;
+
+procedure TTestArgon2.TestVectorsFromInternetDraft;
+var
+  LAdditional, LSecret, LSalt, LPassword: String;
+  Argon2Version: TArgon2Version;
+  Argon2Type: TArgon2Type;
+begin
+
+  LAdditional := '040404040404040404040404';
+  LSecret := '0303030303030303';
+  LSalt := '02020202020202020202020202020202';
+  LPassword :=
+    '0101010101010101010101010101010101010101010101010101010101010101';
+
+  Argon2Version := TArgon2Version.a2vARGON2_VERSION_13;
+
+  Argon2Type := TArgon2Type.a2tARGON2_d;
+
+  HashTestFromInternetDraft(Argon2Type, Argon2Version, 3, 32, 4, LAdditional,
+    LSecret, LSalt, LPassword,
+    '512B391B6F1162975371D30919734294F868E3BE3984F3C1A13A4DB9FABE4ACB',
+    DEFAULT_OUTPUTLEN_IN_BITS);
+
+  Argon2Type := TArgon2Type.a2tARGON2_i;
+
+  HashTestFromInternetDraft(Argon2Type, Argon2Version, 3, 32, 4, LAdditional,
+    LSecret, LSalt, LPassword,
+    'C814D9D1DC7F37AA13F0D77F2494BDA1C8DE6B016DD388D29952A4C4672B6CE8',
+    DEFAULT_OUTPUTLEN_IN_BITS);
+
+  Argon2Type := TArgon2Type.a2tARGON2_id;
+
+  HashTestFromInternetDraft(Argon2Type, Argon2Version, 3, 32, 4, LAdditional,
+    LSecret, LSalt, LPassword,
+    '0D640DF58D78766C08C037A34A8B53C9D01EF0452D75B65EB52520E96B01E659',
+    DEFAULT_OUTPUTLEN_IN_BITS);
+
+end;
+
+procedure TTestArgon2.TestOthers;
+var
+  Argon2Version: TArgon2Version;
+  Argon2Type: TArgon2Type;
+begin
+
+  Argon2Version := TArgon2Version.a2vARGON2_VERSION_10;
+  Argon2Type := TArgon2Type.a2tARGON2_i;
+
+  // Multiple test cases for various input values
+  HashTestOthers(Argon2Type, Argon2Version, 2, 16, 1, 'password', 'somesalt',
+    'F6C4DB4A54E2A370627AFF3DB6176B94A2A209A62C8E36152711802F7B30C694',
+    DEFAULT_OUTPUTLEN_IN_BITS);
+
+  HashTestOthers(Argon2Type, Argon2Version, 2, 20, 1, 'password', 'somesalt',
+    '9690EC55D28D3ED32562F2E73EA62B02B018757643A2AE6E79528459DE8106E9',
+    DEFAULT_OUTPUTLEN_IN_BITS);
+
+  HashTestOthers(Argon2Type, Argon2Version, 2, 18, 1, 'password', 'somesalt',
+    '3E689AAA3D28A77CF2BC72A51AC53166761751182F1EE292E3F677A7DA4C2467',
+    DEFAULT_OUTPUTLEN_IN_BITS);
+
+  HashTestOthers(Argon2Type, Argon2Version, 2, 8, 1, 'password', 'somesalt',
+    'FD4DD83D762C49BDEAF57C47BDCD0C2F1BABF863FDEB490DF63EDE9975FCCF06',
+    DEFAULT_OUTPUTLEN_IN_BITS);
+  HashTestOthers(Argon2Type, Argon2Version, 2, 8, 2, 'password', 'somesalt',
+    'B6C11560A6A9D61EAC706B79A2F97D68B4463AA3AD87E00C07E2B01E90C564FB',
+    DEFAULT_OUTPUTLEN_IN_BITS);
+  HashTestOthers(Argon2Type, Argon2Version, 1, 16, 1, 'password', 'somesalt',
+    '81630552B8F3B1F48CDB1992C4C678643D490B2B5EB4FF6C4B3438B5621724B2',
+    DEFAULT_OUTPUTLEN_IN_BITS);
+  HashTestOthers(Argon2Type, Argon2Version, 4, 16, 1, 'password', 'somesalt',
+    'F212F01615E6EB5D74734DC3EF40ADE2D51D052468D8C69440A3A1F2C1C2847B',
+    DEFAULT_OUTPUTLEN_IN_BITS);
+  HashTestOthers(Argon2Type, Argon2Version, 2, 16, 1, 'differentpassword',
+    'somesalt',
+    'E9C902074B6754531A3A0BE519E5BAF404B30CE69B3F01AC3BF21229960109A3',
+    DEFAULT_OUTPUTLEN_IN_BITS);
+  HashTestOthers(Argon2Type, Argon2Version, 2, 16, 1, 'password', 'diffsalt',
+    '79A103B90FE8AEF8570CB31FC8B22259778916F8336B7BDAC3892569D4F1C497',
+    DEFAULT_OUTPUTLEN_IN_BITS);
+
+  HashTestOthers(Argon2Type, Argon2Version, 2, 16, 1, 'password', 'diffsalt',
+    '1A097A5D1C80E579583F6E19C7E4763CCB7C522CA85B7D58143738E12CA39F8E6E42734C950FF2463675B97C37BA'
+    + '39FEBA4A9CD9CC5B4C798F2AAF70EB4BD044C8D148DECB569870DBD923430B82A083F284BEAE777812CCE18CDAC68EE8CCEF'
+    + 'C6EC9789F30A6B5A034591F51AF830F4', 112 * 8);
+
+  Argon2Version := TArgon2Version.a2vARGON2_VERSION_13;
+  Argon2Type := TArgon2Type.a2tARGON2_i;
+  // Multiple test cases for various input values
+
+  HashTestOthers(Argon2Type, Argon2Version, 2, 16, 1, 'password', 'somesalt',
+    'C1628832147D9720C5BD1CFD61367078729F6DFB6F8FEA9FF98158E0D7816ED0',
+    DEFAULT_OUTPUTLEN_IN_BITS);
+
+  HashTestOthers(Argon2Type, Argon2Version, 2, 20, 1, 'password', 'somesalt',
+    'D1587ACA0922C3B5D6A83EDAB31BEE3C4EBAEF342ED6127A55D19B2351AD1F41',
+    DEFAULT_OUTPUTLEN_IN_BITS);
+
+  HashTestOthers(Argon2Type, Argon2Version, 2, 18, 1, 'password', 'somesalt',
+    '296DBAE80B807CDCEAAD44AE741B506F14DB0959267B183B118F9B24229BC7CB',
+    DEFAULT_OUTPUTLEN_IN_BITS);
+
+  HashTestOthers(Argon2Type, Argon2Version, 2, 8, 1, 'password', 'somesalt',
+    '89E9029F4637B295BEB027056A7336C414FADD43F6B208645281CB214A56452F',
+    DEFAULT_OUTPUTLEN_IN_BITS);
+
+  HashTestOthers(Argon2Type, Argon2Version, 2, 8, 2, 'password', 'somesalt',
+    '4FF5CE2769A1D7F4C8A491DF09D41A9FBE90E5EB02155A13E4C01E20CD4EAB61',
+    DEFAULT_OUTPUTLEN_IN_BITS);
+  HashTestOthers(Argon2Type, Argon2Version, 1, 16, 1, 'password', 'somesalt',
+    'D168075C4D985E13EBEAE560CF8B94C3B5D8A16C51916B6F4AC2DA3AC11BBECF',
+    DEFAULT_OUTPUTLEN_IN_BITS);
+  HashTestOthers(Argon2Type, Argon2Version, 4, 16, 1, 'password', 'somesalt',
+    'AAA953D58AF3706CE3DF1AEFD4A64A84E31D7F54175231F1285259F88174CE5B',
+    DEFAULT_OUTPUTLEN_IN_BITS);
+  HashTestOthers(Argon2Type, Argon2Version, 2, 16, 1, 'differentpassword',
+    'somesalt',
+    '14AE8DA01AFEA8700C2358DCEF7C5358D9021282BD88663A4562F59FB74D22EE',
+    DEFAULT_OUTPUTLEN_IN_BITS);
+  HashTestOthers(Argon2Type, Argon2Version, 2, 16, 1, 'password', 'diffsalt',
+    'B0357CCCFBEF91F3860B0DBA447B2348CBEFECADAF990ABFE9CC40726C521271',
+    DEFAULT_OUTPUTLEN_IN_BITS);
+
+end;
+
+initialization
+
+// Register any test cases with the test runner
+
+{$IFDEF FPC}
+  RegisterTest(TTestArgon2);
+{$ELSE}
+  RegisterTest(TTestArgon2.Suite);
+{$ENDIF FPC}
+
+end.

+ 4 - 4
CryptoLib.Tests/src/Crypto/DSATests.pas

@@ -204,8 +204,8 @@ begin
 
   if (not TArrayUtils.AreEqual(sigBytes, sig)) then
   begin
-    Fail(TConverters.ConvertBytesToString(&message, TEncoding.UTF8) +
-      ' signature incorrect');
+    Fail(Format('%s %s', [TConverters.ConvertBytesToString(&message,
+      TEncoding.UTF8), 'signature incorrect']));
   end;
 
   sgr.Init(false, vKey);
@@ -214,8 +214,8 @@ begin
 
   if (not(sgr.VerifySignature(sigBytes))) then
   begin
-    Fail(TConverters.ConvertBytesToString(&message, TEncoding.UTF8) +
-      ' verification failed');
+    Fail(Format('%s %s', [TConverters.ConvertBytesToString(&message,
+      TEncoding.UTF8), 'verification failed']));
   end;
 end;
 

+ 24 - 0
CryptoLib.Tests/src/Crypto/HMacTests.pas

@@ -63,6 +63,7 @@ type
     FkeyBytes, Fmessage, Foutput1, FoutputMD5, FoutputMD2, FoutputMD4,
       Foutput224, Foutput256, Foutput384, Foutput512, Foutput512_224,
       Foutput512_256, FoutputRipeMD128, FoutputRipeMD160, FoutputTiger,
+      FoutputKck224, FoutputKck256, FoutputKck288, FoutputKck384, FoutputKck512,
       FoutputSha3_224, FoutputSha3_256, FoutputSha3_384, FoutputSha3_512,
       FoutputGost2012_256, FoutputGost2012_512: TBytes;
 
@@ -187,6 +188,17 @@ begin
   FoutputTiger := THex.Decode
     ('1d7a658c75f8f004916e7b07e2a2e10aec7de2ae124d3647');
 
+  FoutputKck224 := THex.Decode
+    ('b73d595a2ba9af815e9f2b4e53e78581ebd34a80b3bbaac4e702c4cc');
+  FoutputKck256 := THex.Decode
+    ('9663d10c73ee294054dc9faf95647cb99731d12210ff7075fb3d3395abfb9821');
+  FoutputKck288 := THex.Decode
+    ('36145df8742160a1811139494d708f9a12757c30dedc622a98aa6ecb69da32a34ea55441');
+  FoutputKck384 := THex.Decode
+    ('892dfdf5d51e4679bf320cd16d4c9dc6f749744608e003add7fba894acff87361efa4e5799be06b6461f43b60ae97048');
+  FoutputKck512 := THex.Decode
+    ('8852c63be8cfc21541a4ee5e5a9a852fc2f7a9adec2ff3a13718ab4ed81aaea0b87b7eb397323548e261a64e7fc75198f6663a11b22cd957f7c8ec858a1c7755');
+
   FoutputSha3_224 := THex.Decode
     ('3b16546bbc7be2706a031dcafd56373d9884367641d8c59af3c860f7');
   FoutputSha3_256 := THex.Decode
@@ -229,6 +241,12 @@ begin
 
   DoTestHMac('HMac-TIGER', FoutputTiger);
 
+  DoTestHMac('HMac-KECCAK224', 224, FoutputKck224);
+  DoTestHMac('HMac-KECCAK256', 256, FoutputKck256);
+  DoTestHMac('HMac-KECCAK288', 288, FoutputKck288);
+  DoTestHMac('HMac-KECCAK384', 384, FoutputKck384);
+  DoTestHMac('HMac-KECCAK512', 512, FoutputKck512);
+
   DoTestHMac('HMac-SHA3-224', 224, FoutputSha3_224);
   DoTestHMac('HMac-SHA3-256', 256, FoutputSha3_256);
   DoTestHMac('HMac-SHA3-384', 384, FoutputSha3_384);
@@ -252,6 +270,12 @@ begin
   DoTestHMac('HMac/RIPEMD160', FoutputRipeMD160);
   DoTestHMac('HMac/TIGER', FoutputTiger);
 
+  DoTestHMac('HMac/KECCAK224', 224, FoutputKck224);
+  DoTestHMac('HMac/KECCAK256', 256, FoutputKck256);
+  DoTestHMac('HMac/KECCAK288', 288, FoutputKck288);
+  DoTestHMac('HMac/KECCAK384', 384, FoutputKck384);
+  DoTestHMac('HMac/KECCAK512', 512, FoutputKck512);
+
   DoTestHMac('HMac/SHA3-224', 224, FoutputSha3_224);
   DoTestHMac('HMac/SHA3-256', 256, FoutputSha3_256);
   DoTestHMac('HMac/SHA3-384', 384, FoutputSha3_384);

+ 174 - 0
CryptoLib.Tests/src/Crypto/Kdf1GeneratorTests.pas

@@ -0,0 +1,174 @@
+{ *********************************************************************************** }
+{ *                              CryptoLib Library                                  * }
+{ *                Copyright (c) 2018 - 20XX Ugochukwu Mmaduekwe                    * }
+{ *                 Github Repository <https://github.com/Xor-el>                   * }
+
+{ *  Distributed under the MIT software license, see the accompanying file LICENSE  * }
+{ *          or visit http://www.opensource.org/licenses/mit-license.php.           * }
+
+{ *                              Acknowledgements:                                  * }
+{ *                                                                                 * }
+{ *      Thanks to Sphere 10 Software (http://www.sphere10.com/) for sponsoring     * }
+{ *                           development of this library                           * }
+
+{ * ******************************************************************************* * }
+
+(* &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&& *)
+
+unit Kdf1GeneratorTests;
+
+interface
+
+{$IFDEF FPC}
+{$MODE DELPHI}
+{$ENDIF FPC}
+
+uses
+  SysUtils,
+{$IFDEF FPC}
+  fpcunit,
+  testregistry,
+{$ELSE}
+  TestFramework,
+{$ENDIF FPC}
+  ClpDigestUtilities,
+  ClpShortenedDigest,
+  ClpIShortenedDigest,
+  ClpIDerivationFunction,
+  ClpIIso18033KdfParameters,
+  ClpIso18033KdfParameters,
+  ClpKdf1BytesGenerator,
+  ClpIKdf1BytesGenerator,
+  ClpEncoders,
+  ClpArrayUtils,
+  ClpCryptoLibTypes;
+
+type
+
+  TCryptoLibTestCase = class abstract(TTestCase)
+
+  end;
+
+type
+
+  /// <summary>
+  /// KDF1 tests - vectors from ISO 18033.
+  /// </summary>
+  TTestKdf1Generator = class(TCryptoLibTestCase)
+  private
+  var
+    Fseed1, Fmask1, Fseed2, Fmask2, Fseed3, Fmask3: TCryptoLibByteArray;
+
+    procedure CheckMask(count: Int32; const kdf: IDerivationFunction;
+      const seed, result: TCryptoLibByteArray);
+    procedure DoTestKdf1Generator();
+
+  protected
+    procedure SetUp; override;
+    procedure TearDown; override;
+  published
+
+    procedure TestKdf1Generator;
+
+  end;
+
+implementation
+
+{ TTestKdf1Generator }
+
+procedure TTestKdf1Generator.CheckMask(count: Int32;
+  const kdf: IDerivationFunction; const seed, result: TCryptoLibByteArray);
+var
+  data: TCryptoLibByteArray;
+begin
+  System.SetLength(data, System.Length(result));
+
+  kdf.Init(TIso18033KdfParameters.Create(seed) as IIso18033KdfParameters);
+
+  kdf.GenerateBytes(data, 0, System.Length(data));
+
+  if (not TArrayUtils.AreEqual(result, data)) then
+  begin
+    Fail(Format('KDF1 failed generator test %d', [count]));
+  end;
+end;
+
+procedure TTestKdf1Generator.DoTestKdf1Generator;
+var
+  temp: TCryptoLibByteArray;
+begin
+
+  CheckMask(1, TKdf1BytesGenerator.Create(TShortenedDigest.Create
+    (TDigestUtilities.GetDigest('SHA-256'), 20) as IShortenedDigest)
+    as IKdf1BytesGenerator, Fseed1, Fmask1);
+
+  CheckMask(2, TKdf1BytesGenerator.Create(TDigestUtilities.GetDigest('SHA-1'))
+    as IKdf1BytesGenerator, Fseed2, Fmask2);
+
+  CheckMask(3, TKdf1BytesGenerator.Create(TShortenedDigest.Create
+    (TDigestUtilities.GetDigest('SHA-256'), 20) as IShortenedDigest)
+    as IKdf1BytesGenerator, Fseed3, Fmask3);
+
+  try
+    System.SetLength(temp, 10);
+    (TKdf1BytesGenerator.Create(TDigestUtilities.GetDigest('SHA-1'))
+      as IKdf1BytesGenerator).GenerateBytes(temp, 0, 20);
+    Fail('short input array not caught');
+  except
+    on e: EDataLengthCryptoLibException do
+    begin
+      // expected
+    end;
+
+  end;
+end;
+
+procedure TTestKdf1Generator.SetUp;
+begin
+  inherited;
+  Fseed1 := THex.Decode('d6e168c5f256a2dcff7ef12facd390f393c7a88d');
+  Fmask1 := THex.Decode('0742ba966813af75536bb6149cc44fc256fd6406df79665bc31dc5'
+    + 'a62f70535e52c53015b9d37d412ff3c1193439599e1b628774c50d9c' +
+    'cb78d82c425e4521ee47b8c36a4bcffe8b8112a89312fc04420a39de' +
+    '99223890e74ce10378bc515a212b97b8a6447ba6a8870278');
+
+  Fseed2 := THex.Decode
+    ('032e45326fa859a72ec235acff929b15d1372e30b207255f0611b8f785d7643741' +
+    '52e0ac009e509e7ba30cd2f1778e113b64e135cf4e2292c75efe5288edfda4');
+  Fmask2 := THex.Decode
+    ('5f8de105b5e96b2e490ddecbd147dd1def7e3b8e0e6a26eb7b956ccb8b3bdc1ca9' +
+    '75bc57c3989e8fbad31a224655d800c46954840ff32052cdf0d640562bdfadfa263c' +
+    'fccf3c52b29f2af4a1869959bc77f854cf15bd7a25192985a842dbff8e13efee5b7e' +
+    '7e55bbe4d389647c686a9a9ab3fb889b2d7767d3837eea4e0a2f04');
+
+  Fseed3 := Fseed2;
+
+  Fmask3 := THex.Decode
+    ('09e2decf2a6e1666c2f6071ff4298305e2643fd510a2403db42a8743cb989de86e' +
+    '668d168cbe604611ac179f819a3d18412e9eb45668f2923c087c12fee0c5a0d2a8aa' +
+    '70185401fbbd99379ec76c663e875a60b4aacb1319fa11c3365a8b79a44669f26fb5' +
+    '55c80391847b05eca1cb5cf8c2d531448d33fbaca19f6410ee1fcb');
+end;
+
+procedure TTestKdf1Generator.TearDown;
+begin
+  inherited;
+
+end;
+
+procedure TTestKdf1Generator.TestKdf1Generator;
+begin
+  DoTestKdf1Generator();
+end;
+
+initialization
+
+// Register any test cases with the test runner
+
+{$IFDEF FPC}
+  RegisterTest(TTestKdf1Generator);
+{$ELSE}
+  RegisterTest(TTestKdf1Generator.Suite);
+{$ENDIF FPC}
+
+end.

+ 194 - 0
CryptoLib.Tests/src/Crypto/Kdf2GeneratorTests.pas

@@ -0,0 +1,194 @@
+{ *********************************************************************************** }
+{ *                              CryptoLib Library                                  * }
+{ *                Copyright (c) 2018 - 20XX Ugochukwu Mmaduekwe                    * }
+{ *                 Github Repository <https://github.com/Xor-el>                   * }
+
+{ *  Distributed under the MIT software license, see the accompanying file LICENSE  * }
+{ *          or visit http://www.opensource.org/licenses/mit-license.php.           * }
+
+{ *                              Acknowledgements:                                  * }
+{ *                                                                                 * }
+{ *      Thanks to Sphere 10 Software (http://www.sphere10.com/) for sponsoring     * }
+{ *                           development of this library                           * }
+
+{ * ******************************************************************************* * }
+
+(* &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&& *)
+
+unit Kdf2GeneratorTests;
+
+interface
+
+{$IFDEF FPC}
+{$MODE DELPHI}
+{$ENDIF FPC}
+
+uses
+  SysUtils,
+{$IFDEF FPC}
+  fpcunit,
+  testregistry,
+{$ELSE}
+  TestFramework,
+{$ENDIF FPC}
+  ClpDigestUtilities,
+  ClpShortenedDigest,
+  ClpIShortenedDigest,
+  ClpIDerivationFunction,
+  ClpKdfParameters,
+  ClpIKdfParameters,
+  ClpKdf2BytesGenerator,
+  ClpIKdf2BytesGenerator,
+  ClpEncoders,
+  ClpArrayUtils,
+  ClpCryptoLibTypes;
+
+type
+
+  TCryptoLibTestCase = class abstract(TTestCase)
+
+  end;
+
+type
+
+  /// <summary>
+  /// KDF2 tests - vectors from ISO 18033.
+  /// </summary>
+  TTestKdf2Generator = class(TCryptoLibTestCase)
+  private
+  var
+    Fseed1, Fmask1, Fseed2, Fmask2, Fseed3, Fmask3, Fseed4, Fmask4,
+      FadjustedMask2, Fsha1Mask: TCryptoLibByteArray;
+
+    procedure CheckMask(count: Int32; const kdf: IDerivationFunction;
+      const seed, result: TCryptoLibByteArray);
+    procedure DoTestKdf2Generator();
+
+  protected
+    procedure SetUp; override;
+    procedure TearDown; override;
+  published
+
+    procedure TestKdf2Generator;
+
+  end;
+
+implementation
+
+{ TTestKdf2Generator }
+
+procedure TTestKdf2Generator.CheckMask(count: Int32;
+  const kdf: IDerivationFunction; const seed, result: TCryptoLibByteArray);
+var
+  data: TCryptoLibByteArray;
+begin
+  System.SetLength(data, System.Length(result));
+
+  kdf.Init(TKdfParameters.Create(seed, Nil) as IKdfParameters);
+
+  kdf.GenerateBytes(data, 0, System.Length(data));
+
+  if (not TArrayUtils.AreEqual(result, data)) then
+  begin
+    Fail(Format('KDF2 failed generator test %d', [count]));
+  end;
+end;
+
+procedure TTestKdf2Generator.DoTestKdf2Generator;
+var
+  temp: TCryptoLibByteArray;
+begin
+
+  CheckMask(1, TKdf2BytesGenerator.Create(TShortenedDigest.Create
+    (TDigestUtilities.GetDigest('SHA-256'), 20) as IShortenedDigest)
+    as IKdf2BytesGenerator, Fseed1, Fmask1);
+
+  CheckMask(2, TKdf2BytesGenerator.Create(TShortenedDigest.Create
+    (TDigestUtilities.GetDigest('SHA-256'), 20) as IShortenedDigest)
+    as IKdf2BytesGenerator, Fseed2, Fmask2);
+
+  CheckMask(3, TKdf2BytesGenerator.Create(TDigestUtilities.GetDigest('SHA-256'))
+    as IKdf2BytesGenerator, Fseed2, FadjustedMask2);
+
+  CheckMask(4, TKdf2BytesGenerator.Create(TDigestUtilities.GetDigest('SHA-1'))
+    as IKdf2BytesGenerator, Fseed2, Fsha1Mask);
+
+  CheckMask(5, TKdf2BytesGenerator.Create(TDigestUtilities.GetDigest('SHA-1'))
+    as IKdf2BytesGenerator, Fseed3, Fmask3);
+
+  CheckMask(6, TKdf2BytesGenerator.Create(TDigestUtilities.GetDigest('SHA-1'))
+    as IKdf2BytesGenerator, Fseed4, Fmask4);
+
+  try
+    System.SetLength(temp, 10);
+    (TKdf2BytesGenerator.Create(TDigestUtilities.GetDigest('SHA-1'))
+      as IKdf2BytesGenerator).GenerateBytes(temp, 0, 20);
+    Fail('short input array not caught');
+  except
+    on e: EDataLengthCryptoLibException do
+    begin
+      // expected
+    end;
+
+  end;
+end;
+
+procedure TTestKdf2Generator.SetUp;
+begin
+  inherited;
+  Fseed1 := THex.Decode('d6e168c5f256a2dcff7ef12facd390f393c7a88d');
+  Fmask1 := THex.Decode('df79665bc31dc5a62f70535e52c53015b9d37d412ff3c119343959'
+    + '9e1b628774c50d9ccb78d82c425e4521ee47b8c36a4bcffe8b8112a8' +
+    '9312fc04420a39de99223890e74ce10378bc515a212b97b8a6447ba6' +
+    'a8870278f0262727ca041fa1aa9f7b5d1cf7f308232fe861');
+
+  Fseed2 := THex.Decode
+    ('032e45326fa859a72ec235acff929b15d1372e30b207255f0611b8f785d7643741' +
+    '52e0ac009e509e7ba30cd2f1778e113b64e135cf4e2292c75efe5288edfda4');
+  Fmask2 := THex.Decode
+    ('10a2403db42a8743cb989de86e668d168cbe604611ac179f819a3d18412e9eb456' +
+    '68f2923c087c12fee0c5a0d2a8aa70185401fbbd99379ec76c663e875a60b4aacb13' +
+    '19fa11c3365a8b79a44669f26fb555c80391847b05eca1cb5cf8c2d531448d33fbac' +
+    'a19f6410ee1fcb260892670e0814c348664f6a7248aaf998a3acc6');
+  FadjustedMask2 := THex.Decode
+    ('10a2403db42a8743cb989de86e668d168cbe6046e23ff26f741e87949a3bba1311ac1' +
+    '79f819a3d18412e9eb45668f2923c087c1299005f8d5fd42ca257bc93e8fee0c5a0d2' +
+    'a8aa70185401fbbd99379ec76c663e9a29d0b70f3fe261a59cdc24875a60b4aacb131' +
+    '9fa11c3365a8b79a44669f26fba933d012db213d7e3b16349');
+
+  Fsha1Mask := THex.Decode
+    ('0e6a26eb7b956ccb8b3bdc1ca975bc57c3989e8fbad31a224655d800c46954840ff32' +
+    '052cdf0d640562bdfadfa263cfccf3c52b29f2af4a1869959bc77f854cf15bd7a2519' +
+    '2985a842dbff8e13efee5b7e7e55bbe4d389647c686a9a9ab3fb889b2d7767d3837ee' +
+    'a4e0a2f04b53ca8f50fb31225c1be2d0126c8c7a4753b0807');
+
+  Fseed3 := THex.Decode('CA7C0F8C3FFA87A96E1B74AC8E6AF594347BB40A');
+  Fmask3 := THex.Decode('744AB703F5BC082E59185F6D049D2D367DB245C2');
+
+  Fseed4 := THex.Decode('0499B502FC8B5BAFB0F4047E731D1F9FD8CD0D8881');
+  Fmask4 := THex.Decode
+    ('03C62280C894E103C680B13CD4B4AE740A5EF0C72547292F82DC6B1777F47D63BA9D1EA732DBF386');
+end;
+
+procedure TTestKdf2Generator.TearDown;
+begin
+  inherited;
+
+end;
+
+procedure TTestKdf2Generator.TestKdf2Generator;
+begin
+  DoTestKdf2Generator();
+end;
+
+initialization
+
+// Register any test cases with the test runner
+
+{$IFDEF FPC}
+  RegisterTest(TTestKdf2Generator);
+{$ELSE}
+  RegisterTest(TTestKdf2Generator.Suite);
+{$ENDIF FPC}
+
+end.

+ 1 - 1
CryptoLib.Tests/src/Crypto/PaddingTests.pas

@@ -253,7 +253,7 @@ begin
   //
   if (ZeroVector <> Nil) then
   begin
-    TArrayUtils.Fill(data, 0, 8, Byte(0));
+    TArrayUtils.ZeroFill(data);
     padding.AddPadding(data, 4);
 
     if (not TArrayUtils.AreEqual(data, ZeroVector)) then

+ 28 - 1
CryptoLib.Tests/src/Crypto/Pkcs5Tests.pas

@@ -114,6 +114,8 @@ begin
     Fail('PBKDF2 HMAC-SHA1 with iteration count "5", 64 bits key generation test failed');
   end;
 
+  generator.Clear();
+
   PasswordString :=
     'All n-entities must communicate with other n-entities via n-1 entiteeheehees';
   PasswordBytes := TConverters.ConvertStringToBytes(PasswordString,
@@ -128,6 +130,8 @@ begin
     Fail('PBKDF2 HMAC-SHA1 with iteration count "500", 192 bits key generation test failed');
   end;
 
+  generator.Clear();
+
   generator.Init(PasswordBytes, SaltBytes, 60000);
 
   if (not TArrayUtils.AreEqual((generator.GenerateDerivedMacParameters(192)
@@ -137,6 +141,8 @@ begin
     Fail('PBKDF2 HMAC-SHA1 with iteration count "60000", 192 bits key generation test failed');
   end;
 
+  generator.Clear();
+
   // https://github.com/ircmaxell/PHP-PasswordLib/blob/master/test/Data/Vectors/pbkdf2-draft-josefsson-sha1.test-vectors
 
   generator := TPkcs5S2ParametersGenerator.Create
@@ -166,6 +172,8 @@ begin
       [iteration_count, dkLen]));
   end;
 
+  generator.Clear();
+
   // 2
 
   iteration_count := 2;
@@ -183,6 +191,8 @@ begin
       [iteration_count, dkLen]));
   end;
 
+  generator.Clear();
+
 
   // 3
 
@@ -201,6 +211,8 @@ begin
       [iteration_count, dkLen]));
   end;
 
+  generator.Clear();
+
   // 4
   // commented out because iteration_count is very large
   // iteration_count := 16777216;
@@ -217,6 +229,8 @@ begin
   // ('PBKDF2 HMAC-SHA1 with iteration count "%u", %u bits key generation test failed',
   // [iteration_count, dkLen]));
   // end;
+  //
+  // generator.Clear();
 
 
   // 5
@@ -243,6 +257,8 @@ begin
       [iteration_count, dkLen]));
   end;
 
+  generator.Clear();
+
 
   // 6
 
@@ -269,6 +285,8 @@ begin
       [iteration_count, dkLen]));
   end;
 
+  generator.Clear();
+
 end;
 
 procedure TTestPkcs5.TestPkcs5_WITH_SHA256;
@@ -309,6 +327,8 @@ begin
       [iteration_count, dkLen]));
   end;
 
+  generator.Clear();
+
   // 2
 
   iteration_count := 2;
@@ -327,6 +347,7 @@ begin
       [iteration_count, dkLen]));
   end;
 
+  generator.Clear();
 
   // 3
 
@@ -346,6 +367,8 @@ begin
       [iteration_count, dkLen]));
   end;
 
+  generator.Clear();
+
   // 4
   // commented out because iteration_count is very large
   // iteration_count := 16777216;
@@ -363,7 +386,8 @@ begin
   // ('PBKDF2 HMAC-SHA256 with iteration count "%u", %u bits key generation test failed',
   // [iteration_count, dkLen]));
   // end;
-
+  //
+  // generator.Clear();
 
   // 5
 
@@ -391,6 +415,7 @@ begin
       [iteration_count, dkLen]));
   end;
 
+  generator.Clear();
 
   // 6
 
@@ -417,6 +442,8 @@ begin
       [iteration_count, dkLen]));
   end;
 
+  generator.Clear();
+
 end;
 
 initialization

+ 250 - 0
CryptoLib.Tests/src/Crypto/ScryptTests.pas

@@ -0,0 +1,250 @@
+{ *********************************************************************************** }
+{ *                              CryptoLib Library                                  * }
+{ *                Copyright (c) 2018 - 20XX Ugochukwu Mmaduekwe                    * }
+{ *                 Github Repository <https://github.com/Xor-el>                   * }
+
+{ *  Distributed under the MIT software license, see the accompanying file LICENSE  * }
+{ *          or visit http://www.opensource.org/licenses/mit-license.php.           * }
+
+{ *                              Acknowledgements:                                  * }
+{ *                                                                                 * }
+{ *      Thanks to Sphere 10 Software (http://www.sphere10.com/) for sponsoring     * }
+{ *                           development of this library                           * }
+
+{ * ******************************************************************************* * }
+
+(* &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&& *)
+
+unit ScryptTests;
+
+interface
+
+{$IFDEF FPC}
+{$MODE DELPHI}
+{$ENDIF FPC}
+
+uses
+  SysUtils,
+{$IFDEF FPC}
+  fpcunit,
+  testregistry,
+{$ELSE}
+  TestFramework,
+{$ENDIF FPC}
+  ClpIKeyParameter,
+  ClpScryptParametersGenerator,
+  ClpIScryptParametersGenerator,
+  ClpConverters,
+  HlpHashLibTypes,
+  ClpCryptoLibTypes;
+
+type
+
+  TCryptoLibTestCase = class abstract(TTestCase)
+
+  end;
+
+type
+
+  /// <summary>
+  /// A Test class for Scrypt.
+  /// </summary>
+  TTestScrypt = class(TCryptoLibTestCase)
+
+  private
+
+    const
+    // multiplied by 8 to get it in bits
+    DEFAULT_OUTPUTLEN_IN_BITS = Int32(64 * 8);
+    ONE_AS_OUTPUTLEN_IN_BITS = Int32(1 * 8);
+
+  var
+    FExpectedString, FActualString: String;
+
+    function DoTestVector(const APassword, ASalt: String;
+      ACost, ABlockSize, AParallelism, AOutputSize: Int32): String;
+
+    procedure DoCheckOk(const AMsg: String; const APassword, ASalt: TBytes;
+      ACost, ABlockSize, AParallelism, AOutputSize: Int32);
+
+    procedure DoCheckIllegal(const AMsg: String; const APassword, ASalt: TBytes;
+      ACost, ABlockSize, AParallelism, AOutputSize: Int32);
+
+  protected
+    procedure SetUp; override;
+    procedure TearDown; override;
+  published
+
+    procedure TestVectors;
+    procedure TestParameters;
+
+  end;
+
+implementation
+
+{ TTestScrypt }
+
+procedure TTestScrypt.SetUp;
+begin
+  inherited;
+
+end;
+
+procedure TTestScrypt.TearDown;
+begin
+  inherited;
+
+end;
+
+function TTestScrypt.DoTestVector(const APassword, ASalt: String;
+  ACost, ABlockSize, AParallelism, AOutputSize: Int32): String;
+var
+  LScryptGenerator: IScryptParametersGenerator;
+  APasswordBytes, ASaltBytes, OutputBytes: TBytes;
+begin
+  APasswordBytes := TConverters.ConvertStringToBytes(APassword,
+    TEncoding.ASCII);
+  ASaltBytes := TConverters.ConvertStringToBytes(ASalt, TEncoding.ASCII);
+
+  LScryptGenerator := TScryptParametersGenerator.Create();
+
+  //
+  // Set the parameters.
+  //
+
+  LScryptGenerator.Init(APasswordBytes, ASaltBytes, ACost, ABlockSize,
+    AParallelism);
+
+  OutputBytes := (LScryptGenerator.GenerateDerivedMacParameters(AOutputSize)
+    as IKeyParameter).GetKey();
+  LScryptGenerator.Clear();
+  Result := TConverters.ConvertBytesToHexString(OutputBytes, False);
+end;
+
+procedure TTestScrypt.DoCheckIllegal(const AMsg: String;
+  const APassword, ASalt: TBytes; ACost, ABlockSize, AParallelism,
+  AOutputSize: Int32);
+var
+  LScryptGenerator: IScryptParametersGenerator;
+  OutputBytes: TBytes;
+begin
+  try
+
+    LScryptGenerator := TScryptParametersGenerator.Create();
+    //
+    // Set the parameters.
+    //
+    //
+    LScryptGenerator.Init(APassword, ASalt, ACost, ABlockSize, AParallelism);
+
+    OutputBytes := (LScryptGenerator.GenerateDerivedMacParameters(AOutputSize)
+      as IKeyParameter).GetKey();
+
+    Fail(AMsg);
+  except
+    on e: EArgumentHashLibException do
+    begin
+      // pass so we do nothing
+    end;
+  end;
+end;
+
+procedure TTestScrypt.DoCheckOk(const AMsg: String;
+  const APassword, ASalt: TBytes; ACost, ABlockSize, AParallelism,
+  AOutputSize: Int32);
+var
+  LScryptGenerator: IScryptParametersGenerator;
+  OutputBytes: TBytes;
+begin
+  try
+    try
+
+      LScryptGenerator := TScryptParametersGenerator.Create();
+      //
+      // Set the parameters.
+      //
+      //
+      LScryptGenerator.Init(APassword, ASalt, ACost, ABlockSize, AParallelism);
+
+      OutputBytes := (LScryptGenerator.GenerateDerivedMacParameters(AOutputSize)
+        as IKeyParameter).GetKey();
+    except
+      on e: EArgumentHashLibException do
+      begin
+        Fail(AMsg);
+      end;
+    end;
+  finally
+    LScryptGenerator.Clear();
+  end;
+end;
+
+procedure TTestScrypt.TestParameters;
+begin
+  DoCheckOk('Minimal values', Nil, Nil, 2, 1, 1, ONE_AS_OUTPUTLEN_IN_BITS);
+  DoCheckIllegal('Cost parameter must be > 1', Nil, Nil, 1, 1, 1,
+    ONE_AS_OUTPUTLEN_IN_BITS);
+  DoCheckOk('Cost parameter 32768 OK for r = 1', Nil, Nil, 32768, 1, 1,
+    ONE_AS_OUTPUTLEN_IN_BITS);
+  DoCheckIllegal('Cost parameter must < 65536 for r = 1', Nil, Nil, 65536, 1, 1,
+    ONE_AS_OUTPUTLEN_IN_BITS);
+  DoCheckIllegal('Block size must be >= 1', Nil, Nil, 2, 0, 2,
+    ONE_AS_OUTPUTLEN_IN_BITS);
+  DoCheckIllegal('Parallelisation parameter must be >= 1', Nil, Nil, 2, 1, 0,
+    ONE_AS_OUTPUTLEN_IN_BITS);
+  // disabled test because it's very expensive
+  // DoCheckOk('Parallelisation parameter 65535 OK for r = 4', Nil, Nil, 2, 32,
+  // 65535, ONE_AS_OUTPUTLEN_IN_BITS);
+  DoCheckIllegal('Parallelisation parameter must be < 65535 for r = 4', Nil,
+    Nil, 2, 32, 65536, ONE_AS_OUTPUTLEN_IN_BITS);
+
+  DoCheckIllegal('Len parameter must be > 1', Nil, Nil, 2, 1, 1, 0);
+end;
+
+procedure TTestScrypt.TestVectors;
+begin
+
+  FActualString := DoTestVector('', '', 16, 1, 1, DEFAULT_OUTPUTLEN_IN_BITS);
+  FExpectedString :=
+    '77D6576238657B203B19CA42C18A0497F16B4844E3074AE8DFDFFA3FEDE21442FCD0069DED0948F8326A753A0FC81F17E8D3E0FB2E0D3628CF35E20C38D18906';
+
+  CheckEquals(FExpectedString, FActualString, Format('Expected %s but got %s.',
+    [FExpectedString, FActualString]));
+
+  FActualString := DoTestVector('password', 'NaCl', 1024, 8, 16,
+    DEFAULT_OUTPUTLEN_IN_BITS);
+  FExpectedString :=
+    'FDBABE1C9D3472007856E7190D01E9FE7C6AD7CBC8237830E77376634B3731622EAF30D92E22A3886FF109279D9830DAC727AFB94A83EE6D8360CBDFA2CC0640';
+
+  CheckEquals(FExpectedString, FActualString, Format('Expected %s but got %s.',
+    [FExpectedString, FActualString]));
+
+  FActualString := DoTestVector('pleaseletmein', 'SodiumChloride', 16384, 8, 1,
+    DEFAULT_OUTPUTLEN_IN_BITS);
+  FExpectedString :=
+    '7023BDCB3AFD7348461C06CD81FD38EBFDA8FBBA904F8E3EA9B543F6545DA1F2D5432955613F0FCF62D49705242A9AF9E61E85DC0D651E40DFCF017B45575887';
+
+  CheckEquals(FExpectedString, FActualString, Format('Expected %s but got %s.',
+    [FExpectedString, FActualString]));
+
+  FActualString := DoTestVector('pleaseletmein', 'SodiumChloride', 1048576, 8,
+    1, DEFAULT_OUTPUTLEN_IN_BITS);
+  FExpectedString :=
+    '2101CB9B6A511AAEADDBBE09CF70F881EC568D574A2FFD4DABE5EE9820ADAA478E56FD8F4BA5D09FFA1C6D927C40F4C337304049E8A952FBCBF45C6FA77A41A4';
+
+  CheckEquals(FExpectedString, FActualString, Format('Expected %s but got %s.',
+    [FExpectedString, FActualString]));
+
+end;
+
+initialization
+
+// Register any test cases with the test runner
+
+{$IFDEF FPC}
+  RegisterTest(TTestScrypt);
+{$ELSE}
+  RegisterTest(TTestScrypt.Suite);
+{$ENDIF FPC}
+
+end.

+ 39 - 0
CryptoLib.Tests/src/Math/BigIntegerTests.pas

@@ -58,6 +58,7 @@ type
     FRandom: ISecureRandom;
 
     function val(n: Int64): TBigInteger;
+    function IsEvenUsingMod(const n: TBigInteger): Boolean;
     function mersenne(e: Int32): TBigInteger;
     procedure CheckEqualsBigInteger(const a, b: TBigInteger;
       const msg: String = '');
@@ -102,6 +103,7 @@ type
     procedure TestSignValue();
     procedure TestSubtract();
     procedure TestTestBit();
+    procedure TestIsEven();
     procedure TestToByteArray();
     procedure TestToByteArrayUnsigned();
     procedure TestToString();
@@ -124,6 +126,11 @@ begin
   CheckEquals(True, a.Equals(b), msg);
 end;
 
+function TTestBigInteger.IsEvenUsingMod(const n: TBigInteger): Boolean;
+begin
+  result := n.&Mod(TBigInteger.Two).Equals(TBigInteger.Zero);
+end;
+
 function TTestBigInteger.mersenne(e: Int32): TBigInteger;
 begin
   result := Ftwo.Pow(e).Subtract(Fone);
@@ -677,6 +684,38 @@ begin
   // TODO Tests for large numbers
 end;
 
+procedure TTestBigInteger.TestIsEven;
+var
+  RandomBigInteger: TBigInteger;
+  idx: Int32;
+begin
+  CheckTrue(TBigInteger.ValueOf(2).IsEven);
+  CheckTrue(TBigInteger.ValueOf(4).IsEven);
+  CheckTrue(TBigInteger.ValueOf(6).IsEven);
+  CheckTrue(TBigInteger.ValueOf(8).IsEven);
+  CheckTrue(TBigInteger.ValueOf(10).IsEven);
+  CheckTrue(TBigInteger.ValueOf(12).IsEven);
+
+  CheckFalse(TBigInteger.ValueOf(1).IsEven);
+  CheckFalse(TBigInteger.ValueOf(3).IsEven);
+  CheckFalse(TBigInteger.ValueOf(5).IsEven);
+  CheckFalse(TBigInteger.ValueOf(7).IsEven);
+  CheckFalse(TBigInteger.ValueOf(9).IsEven);
+  CheckFalse(TBigInteger.ValueOf(11).IsEven);
+
+  idx := 0;
+
+  while idx <= 1000 do
+  begin
+    RandomBigInteger := TBigInteger.Create(RandomRange(1, 256), FRandom);
+    CheckEquals(RandomBigInteger.IsEven(), IsEvenUsingMod(RandomBigInteger),
+      Format('IsEven Comparison failed with "%s"',
+      [RandomBigInteger.ToString]));
+
+    System.Inc(idx);
+  end;
+end;
+
 procedure TTestBigInteger.TestIsProbablePrime;
 var
   p, c, e: Int32;

+ 2 - 2
CryptoLib.Tests/src/Math/ECPointTests.pas

@@ -654,14 +654,14 @@ begin
   i := 0;
   while i < System.Length(FpInstance.Fp) do
   begin
-    ImplTestAllPoints(FpInstance.Fp[0], FpInstance.FInfinity);
+    ImplTestAllPoints(FpInstance.Fp[i], FpInstance.FInfinity);
     System.Inc(i);
   end;
 
   i := 0;
   while i < System.Length(F2mInstance.Fp) do
   begin
-    ImplTestAllPoints(F2mInstance.Fp[0], F2mInstance.FInfinity);
+    ImplTestAllPoints(F2mInstance.Fp[i], F2mInstance.FInfinity);
     System.Inc(i);
   end;
 end;

+ 6 - 4
CryptoLib.Tests/src/Math/PascalCoinECIESTests.pas

@@ -51,6 +51,7 @@ uses
   ClpIMac,
   ClpMacUtilities,
   ClpIX9ECParameters,
+  ClpConverters,
   ClpCryptoLibTypes;
 
 type
@@ -250,8 +251,8 @@ begin
   CipherEncrypt.Init(True, RecreatePublicKeyFromAffineXandAffineYCoord(keyType,
     THex.Decode(RawAffineXCoord), THex.Decode(RawAffineYCoord)),
     GetPascalCoinIESParameterSpec(), FRandom);
-  Result := THex.Encode(CipherEncrypt.DoFinal(TEncoding.ASCII.GetBytes
-    (UnicodeString(PayloadToEncrypt))));
+  Result := THex.Encode(CipherEncrypt.DoFinal(TConverters.ConvertStringToBytes
+    (PayloadToEncrypt, TEncoding.ASCII)));
 end;
 
 function TTestPascalCoinECIES.DoPascalCoinECIESDecrypt(keyType: TKeyType;
@@ -264,8 +265,9 @@ begin
     CipherDecrypt := TIESCipher.Create(GetECIESPascalCoinCompatibilityEngine());
     CipherDecrypt.Init(False, RecreatePrivateKeyFromByteArray(keyType,
       THex.Decode(RawPrivateKey)), GetPascalCoinIESParameterSpec(), FRandom);
-    Result := String(TEncoding.ASCII.GetString
-      ((CipherDecrypt.DoFinal(THex.Decode(PayloadToDecrypt)))));
+
+    Result := TConverters.ConvertBytesToString
+      (CipherDecrypt.DoFinal(THex.Decode(PayloadToDecrypt)), TEncoding.ASCII);
   except
     // should only happen if decryption fails
     raise;

+ 304 - 0
CryptoLib.Tests/src/Others/DigestTests.pas

@@ -0,0 +1,304 @@
+{ *********************************************************************************** }
+{ *                              CryptoLib Library                                  * }
+{ *                Copyright (c) 2018 - 20XX Ugochukwu Mmaduekwe                    * }
+{ *                 Github Repository <https://github.com/Xor-el>                   * }
+
+{ *  Distributed under the MIT software license, see the accompanying file LICENSE  * }
+{ *          or visit http://www.opensource.org/licenses/mit-license.php.           * }
+
+{ *                              Acknowledgements:                                  * }
+{ *                                                                                 * }
+{ *      Thanks to Sphere 10 Software (http://www.sphere10.com/) for sponsoring     * }
+{ *                           development of this library                           * }
+
+{ * ******************************************************************************* * }
+
+(* &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&& *)
+
+unit DigestTests;
+
+interface
+
+{$IFDEF FPC}
+{$MODE DELPHI}
+{$ENDIF FPC}
+
+uses
+  SysUtils,
+{$IFDEF FPC}
+  fpcunit,
+  testregistry,
+{$ELSE}
+  TestFramework,
+{$ENDIF FPC}
+  ClpMiscObjectIdentifiers,
+  ClpRosstandartObjectIdentifiers,
+  ClpIDigest,
+  ClpDigestUtilities,
+  ClpEncoders,
+  ClpArrayUtils,
+  ClpCryptoLibTypes,
+  ClpConverters;
+
+type
+
+  TCryptoLibTestCase = class abstract(TTestCase)
+
+  end;
+
+type
+
+  TTestDigest = class(TCryptoLibTestCase)
+  private
+  var
+    FabcVectors: TCryptoLibMatrixGenericArray<String>;
+
+    procedure DoTest(const algorithm: String);
+    procedure DoAbcTest(const algorithm, hash: String);
+
+  protected
+    procedure SetUp; override;
+    procedure TearDown; override;
+  published
+    procedure TestDigests();
+
+  end;
+
+implementation
+
+{ TTestDigest }
+
+procedure TTestDigest.SetUp;
+begin
+  inherited;
+  FabcVectors := TCryptoLibMatrixGenericArray<String>.Create
+    (TCryptoLibStringArray.Create('MD2', 'da853b0d3f88d99b30283a69e6ded6bb'),
+    TCryptoLibStringArray.Create('MD4', 'a448017aaf21d8525fc10ae87aa6729d'),
+    TCryptoLibStringArray.Create('MD5', '900150983cd24fb0d6963f7d28e17f72'),
+    TCryptoLibStringArray.Create('SHA-1',
+    'a9993e364706816aba3e25717850c26c9cd0d89d'),
+    TCryptoLibStringArray.Create('SHA-224',
+    '23097d223405d8228642a477bda255b32aadbce4bda0b3f7e36c9da7'),
+    TCryptoLibStringArray.Create('SHA-256',
+    'ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad'),
+    TCryptoLibStringArray.Create('SHA-384',
+    'cb00753f45a35e8bb5a03d699ac65007272c32ab0eded1631a8b605a43ff5bed8086072ba1e7cc2358baeca134c825a7'),
+    TCryptoLibStringArray.Create('SHA-512',
+    'ddaf35a193617abacc417349ae20413112e6fa4e89a97ea20a9eeee64b55d39a2192992a274fc1a836ba3c23a3feebbd454d4423643ce80e2a9ac94fa54ca49f'),
+    TCryptoLibStringArray.Create('SHA-512/224',
+    '4634270F707B6A54DAAE7530460842E20E37ED265CEEE9A43E8924AA'),
+    TCryptoLibStringArray.Create('SHA-512/256',
+    '53048E2681941EF99B2E29B76B4C7DABE4C2D0C634FC6D46E0E2F13107E7AF23'),
+    TCryptoLibStringArray.Create('RIPEMD128',
+    'c14a12199c66e4ba84636b0f69144c77'),
+    TCryptoLibStringArray.Create('RIPEMD160',
+    '8eb208f7e05d987a9b044a8e98c6b087f15a0bfc'),
+    TCryptoLibStringArray.Create('RIPEMD256',
+    'afbd6e228b9d8cbbcef5ca2d03e6dba10ac0bc7dcbe4680e1e42d2e975459b65'),
+    TCryptoLibStringArray.Create('RIPEMD320',
+    'de4c01b3054f8930a79d09ae738e92301e5a17085beffdc1b8d116713e74f82fa942d64cdbc4682d'),
+    TCryptoLibStringArray.Create('Tiger',
+    '2AAB1484E8C158F2BFB8C5FF41B57A525129131C957B5F93'),
+    TCryptoLibStringArray.Create('GOST3411',
+    'b285056dbf18d7392d7677369524dd14747459ed8143997e163b2986f92fd42c'),
+    TCryptoLibStringArray.Create('WHIRLPOOL',
+    '4E2448A4C6F486BB16B6562C73B4020BF3043E3A731BCE721AE1B303D97E6D4C7181EEBDB6C57E277D0E34957114CBD6C797FC9D95D8B582D225292076D4EEF5'),
+    TCryptoLibStringArray.Create('SM3',
+    '66c7f0f462eeedd9d1f2d46bdc10e4e24167c4875cf2f7a2297da02b8f4ba8e0'),
+    TCryptoLibStringArray.Create('SHA3-224',
+    'e642824c3f8cf24ad09234ee7d3c766fc9a3a5168d0c94ad73b46fdf'),
+    TCryptoLibStringArray.Create('SHA3-256',
+    '3a985da74fe225b2045c172d6bd390bd855f086e3e9d525b46bfe24511431532'),
+    TCryptoLibStringArray.Create('SHA3-384',
+    'ec01498288516fc926459f58e2c6ad8df9b473cb0fc08c2596da7cf0e49be4b298d88cea927ac7f539f1edf228376d25'),
+    TCryptoLibStringArray.Create('SHA3-512',
+    'b751850b1a57168a5693cd924b6b096e08f621827444f70d884f5d0240d2712e10e116e9192af3c91a7ec57647e3934057340b4cf408d5a56592f8274eec53f0'),
+    TCryptoLibStringArray.Create('KECCAK-224',
+    'c30411768506ebe1c2871b1ee2e87d38df342317300a9b97a95ec6a8'),
+    TCryptoLibStringArray.Create('KECCAK-256',
+    '4e03657aea45a94fc7d47ba826c8d667c0d1e6e33a64a036ec44f58fa12d6c45'),
+    TCryptoLibStringArray.Create('KECCAK-288',
+    '20ff13d217d5789fa7fc9e0e9a2ee627363ec28171d0b6c52bbd2f240554dbc94289f4d6'),
+    TCryptoLibStringArray.Create('KECCAK-384',
+    'f7df1165f033337be098e7d288ad6a2f74409d7a60b49c36642218de161b1f99f8c681e4afaf31a34db29fb763e3c28e'),
+    TCryptoLibStringArray.Create('KECCAK-512',
+    '18587dc2ea106b9a1563e32b3312421ca164c7f1f07bc922a9c83d77cea3a1e5d0c69910739025372dc14ac9642629379540c17e2a65b19d77aa511a9d00bb96'),
+    TCryptoLibStringArray.Create('BLAKE2B-160',
+    '384264f676f39536840523f284921cdc68b6846b'),
+    TCryptoLibStringArray.Create('BLAKE2B-256',
+    'bddd813c634239723171ef3fee98579b94964e3bb1cb3e427262c8c068d52319'),
+    TCryptoLibStringArray.Create('BLAKE2B-384',
+    '6f56a82c8e7ef526dfe182eb5212f7db9df1317e57815dbda46083fc30f54ee6c66ba83be64b302d7cba6ce15bb556f4'),
+    TCryptoLibStringArray.Create('BLAKE2B-512',
+    'ba80a53f981c4d0d6a2797b69f12f6e94c212f14685ac4b74b12bb6fdbffa2d17d87c5392aab792dc252d5de4533cc9518d38aa8dbf1925ab92386edd4009923'),
+    TCryptoLibStringArray.Create(TMiscObjectIdentifiers.id_blake2b160.Id,
+    '384264f676f39536840523f284921cdc68b6846b'),
+    TCryptoLibStringArray.Create(TMiscObjectIdentifiers.id_blake2b256.Id,
+    'bddd813c634239723171ef3fee98579b94964e3bb1cb3e427262c8c068d52319'),
+    TCryptoLibStringArray.Create(TMiscObjectIdentifiers.id_blake2b384.Id,
+    '6f56a82c8e7ef526dfe182eb5212f7db9df1317e57815dbda46083fc30f54ee6c66ba83be64b302d7cba6ce15bb556f4'),
+    TCryptoLibStringArray.Create(TMiscObjectIdentifiers.id_blake2b512.Id,
+    'ba80a53f981c4d0d6a2797b69f12f6e94c212f14685ac4b74b12bb6fdbffa2d17d87c5392aab792dc252d5de4533cc9518d38aa8dbf1925ab92386edd4009923'),
+    TCryptoLibStringArray.Create('BLAKE2S-128',
+    'aa4938119b1dc7b87cbad0ffd200d0ae'),
+    TCryptoLibStringArray.Create('BLAKE2S-160',
+    '5ae3b99be29b01834c3b508521ede60438f8de17'),
+    TCryptoLibStringArray.Create('BLAKE2S-224',
+    '0b033fc226df7abde29f67a05d3dc62cf271ef3dfea4d387407fbd55'),
+    TCryptoLibStringArray.Create('BLAKE2S-256',
+    '508c5e8c327c14e2e1a72ba34eeb452f37458b209ed63a294d999b4c86675982'),
+    TCryptoLibStringArray.Create(TMiscObjectIdentifiers.id_blake2s128.Id,
+    'aa4938119b1dc7b87cbad0ffd200d0ae'),
+    TCryptoLibStringArray.Create(TMiscObjectIdentifiers.id_blake2s160.Id,
+    '5ae3b99be29b01834c3b508521ede60438f8de17'),
+    TCryptoLibStringArray.Create(TMiscObjectIdentifiers.id_blake2s224.Id,
+    '0b033fc226df7abde29f67a05d3dc62cf271ef3dfea4d387407fbd55'),
+    TCryptoLibStringArray.Create(TMiscObjectIdentifiers.id_blake2s256.Id,
+    '508c5e8c327c14e2e1a72ba34eeb452f37458b209ed63a294d999b4c86675982'),
+    TCryptoLibStringArray.Create('GOST3411-2012-256',
+    '4e2919cf137ed41ec4fb6270c61826cc4fffb660341e0af3688cd0626d23b481'),
+    TCryptoLibStringArray.Create(TRosstandartObjectIdentifiers.
+    id_tc26_gost_3411_12_256.Id,
+    '4e2919cf137ed41ec4fb6270c61826cc4fffb660341e0af3688cd0626d23b481'),
+    TCryptoLibStringArray.Create('GOST3411-2012-512',
+    '28156e28317da7c98f4fe2bed6b542d0dab85bb224445fcedaf75d46e26d7eb8d5997f3e0915dd6b7f0aab08d9c8beb0d8c64bae2ab8b3c8c6bc53b3bf0db728'),
+    TCryptoLibStringArray.Create(TRosstandartObjectIdentifiers.
+    id_tc26_gost_3411_12_512.Id,
+    '28156e28317da7c98f4fe2bed6b542d0dab85bb224445fcedaf75d46e26d7eb8d5997f3e0915dd6b7f0aab08d9c8beb0d8c64bae2ab8b3c8c6bc53b3bf0db728'),
+    TCryptoLibStringArray.Create('DSTU7564-256',
+    '0bd1b36109f1318411a0517315aa46b8839df06622a278676f5487996c9cfc04'));
+end;
+
+procedure TTestDigest.TearDown;
+begin
+  FabcVectors := Nil;
+  inherited;
+end;
+
+procedure TTestDigest.DoAbcTest(const algorithm, hash: String);
+var
+  abc, result: TCryptoLibByteArray;
+  digest: IDigest;
+begin
+  abc := TBytes.Create($61, $62, $63);
+
+  digest := TDigestUtilities.GetDigest(algorithm);
+
+  digest.BlockUpdate(abc, 0, System.Length(abc));
+  result := TDigestUtilities.DoFinal(digest);
+
+  if (not TArrayUtils.AreEqual(result, THex.Decode(hash))) then
+  begin
+    Fail(Format('abc result not equal for %s', [algorithm]));
+  end;
+end;
+
+procedure TTestDigest.DoTest(const algorithm: String);
+var
+  &message, result, result2: TCryptoLibByteArray;
+  digest, d: IDigest;
+  i: Int32;
+begin
+  &message := TConverters.ConvertStringToBytes('hello world', TEncoding.ASCII);
+
+  digest := TDigestUtilities.GetDigest(algorithm);
+
+  digest.BlockUpdate(&message, 0, System.Length(&message));
+  result := TDigestUtilities.DoFinal(digest);
+
+  digest.BlockUpdate(&message, 0, System.Length(&message));
+  result2 := TDigestUtilities.DoFinal(digest);
+
+  // test one digest the same message with the same instance
+  if (not TArrayUtils.AreEqual(result, result2)) then
+  begin
+    Fail('Result object 1 not equal');
+  end;
+
+  // test two, single byte updates
+  for i := 0 to System.Pred(System.Length(&message)) do
+  begin
+    digest.Update(&message[i]);
+  end;
+
+  result2 := TDigestUtilities.DoFinal(digest);
+
+  if (not TArrayUtils.AreEqual(result, result2)) then
+  begin
+    Fail('Result object 2 not equal');
+  end;
+
+  // test three, two half updates
+  digest.BlockUpdate(&message, 0, System.Length(&message) div 2);
+  digest.BlockUpdate(&message, System.Length(&message) div 2,
+    System.Length(&message) - (System.Length(&message) div 2));
+
+  result2 := TDigestUtilities.DoFinal(digest);
+
+  if (not TArrayUtils.AreEqual(result, result2)) then
+  begin
+    Fail('Result object 3 not equal');
+  end;
+
+  // test four, clone test
+  digest.BlockUpdate(&message, 0, System.Length(&message) div 2);
+  d := digest.Clone();
+  digest.BlockUpdate(&message, System.Length(&message) div 2,
+    System.Length(&message) - (System.Length(&message) div 2));
+
+  result2 := TDigestUtilities.DoFinal(digest);
+
+  if (not TArrayUtils.AreEqual(result, result2)) then
+  begin
+    Fail('Result object 4(a) not equal');
+  end;
+
+  d.BlockUpdate(&message, System.Length(&message) div 2, System.Length(&message)
+    - (System.Length(&message) div 2));
+
+  result2 := TDigestUtilities.DoFinal(d);
+
+  if (not TArrayUtils.AreEqual(result, result2)) then
+  begin
+    Fail('Result object 4(b) not equal');
+  end;
+
+  // test five, check reset() method
+  digest.BlockUpdate(&message, 0, System.Length(&message) div 2);
+  digest.Reset();
+  digest.BlockUpdate(&message, 0, System.Length(&message) div 2);
+  digest.BlockUpdate(&message, System.Length(&message) div 2,
+    System.Length(&message) - (System.Length(&message) div 2));
+
+  result2 := TDigestUtilities.DoFinal(digest);
+
+  if (not TArrayUtils.AreEqual(result, result2)) then
+  begin
+    Fail('Result object 5 not equal');
+  end;
+
+end;
+
+procedure TTestDigest.TestDigests;
+var
+  i: Int32;
+begin
+  for i := 0 to System.Pred(System.Length(FabcVectors[0])) do
+  begin
+    DoTest(FabcVectors[i][0]);
+
+    DoAbcTest(FabcVectors[i][0], FabcVectors[i][1]);
+  end;
+end;
+
+initialization
+
+// Register any test cases with the test runner
+
+{$IFDEF FPC}
+  RegisterTest(TTestDigest);
+{$ELSE}
+  RegisterTest(TTestDigest.Suite);
+{$ENDIF FPC}
+
+end.

+ 429 - 0
CryptoLib.Tests/src/Others/Ed25519HigherLevelTests.pas

@@ -0,0 +1,429 @@
+{ *********************************************************************************** }
+{ *                              CryptoLib Library                                  * }
+{ *                Copyright (c) 2018 - 20XX Ugochukwu Mmaduekwe                    * }
+{ *                 Github Repository <https://github.com/Xor-el>                   * }
+
+{ *  Distributed under the MIT software license, see the accompanying file LICENSE  * }
+{ *          or visit http://www.opensource.org/licenses/mit-license.php.           * }
+
+{ *                              Acknowledgements:                                  * }
+{ *                                                                                 * }
+{ *      Thanks to Sphere 10 Software (http://www.sphere10.com/) for sponsoring     * }
+{ *                           development of this library                           * }
+
+{ * ******************************************************************************* * }
+
+(* &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&& *)
+
+unit Ed25519HigherLevelTests;
+
+interface
+
+{$IFDEF FPC}
+{$MODE DELPHI}
+{$ENDIF FPC}
+
+uses
+  SysUtils,
+{$IFDEF FPC}
+  fpcunit,
+  testregistry,
+{$ELSE}
+  TestFramework,
+{$ENDIF FPC}
+  TypInfo,
+  ClpSecureRandom,
+  ClpISecureRandom,
+  ClpISigner,
+  ClpEd25519,
+  ClpEd25519Signer,
+  ClpIEd25519Signer,
+  ClpEd25519CtxSigner,
+  ClpIEd25519CtxSigner,
+  ClpEd25519PhSigner,
+  ClpIEd25519PhSigner,
+  ClpIEd25519PrivateKeyParameters,
+  ClpIEd25519PublicKeyParameters,
+  ClpIEd25519Blake2BPrivateKeyParameters,
+  ClpIEd25519Blake2BPublicKeyParameters,
+  ClpEd25519PrivateKeyParameters,
+  ClpEd25519PublicKeyParameters,
+  ClpEd25519Blake2BPrivateKeyParameters,
+  ClpEd25519Blake2BPublicKeyParameters,
+  ClpIAsymmetricCipherKeyPair,
+  ClpAsymmetricCipherKeyPair,
+  ClpEd25519KeyPairGenerator,
+  ClpIEd25519KeyPairGenerator,
+  ClpEd25519KeyGenerationParameters,
+  ClpIEd25519KeyGenerationParameters,
+  ClpSignerUtilities,
+  ClpArrayUtils,
+  ClpEncoders,
+  ClpCryptoLibTypes;
+
+type
+
+  TCryptoLibTestCase = class abstract(TTestCase)
+
+  end;
+
+type
+
+  /// <summary>
+  /// test vectors gotten from <see href="https://github.com/warner/python-ed25519" />
+  /// and <see href="https://github.com/Matoking/python-ed25519-blake2b" />
+  /// </summary>
+  TTestEd25519HigherLevel = class(TCryptoLibTestCase)
+  private
+  var
+    FRandom: ISecureRandom;
+
+  type
+{$SCOPEDENUMS ON}
+    TEd25519SignerAlgorithm = (Ed25519, Ed25519Blake2B);
+{$SCOPEDENUMS OFF}
+  function CreateSigner(algorithm: TEd25519.TEd25519Algorithm;
+    const context: TCryptoLibByteArray): ISigner;
+
+  function CreateCustomSigner(const algorithm: TEd25519SignerAlgorithm)
+    : ISigner;
+
+  function ReconstructEd25519KeyPair(algorithm: TEd25519SignerAlgorithm;
+    const sk, pk: TCryptoLibByteArray): IAsymmetricCipherKeyPair;
+
+  function RandomContext(length: Int32): TCryptoLibByteArray;
+
+  procedure DoTestConsistency(algorithm: TEd25519.TEd25519Algorithm;
+    const context: TCryptoLibByteArray);
+
+  procedure DoEd25519Test(id: Int32; algorithm: TEd25519SignerAlgorithm;
+    const sk, pk, msg, sig: String);
+  protected
+    procedure SetUp; override;
+    procedure TearDown; override;
+  published
+    procedure TestConsistency();
+    procedure TestEd25519();
+
+  end;
+
+implementation
+
+{ TTestEd25519HigherLevel }
+
+function TTestEd25519HigherLevel.CreateCustomSigner(const algorithm
+  : TEd25519SignerAlgorithm): ISigner;
+var
+  algorithmName: String;
+begin
+  algorithmName := GetEnumName(TypeInfo(TEd25519SignerAlgorithm),
+    Ord(algorithm));
+  Result := TSignerUtilities.GetSigner(algorithmName);
+end;
+
+function TTestEd25519HigherLevel.CreateSigner
+  (algorithm: TEd25519.TEd25519Algorithm;
+  const context: TCryptoLibByteArray): ISigner;
+begin
+  case algorithm of
+    TEd25519.TEd25519Algorithm.Ed25519:
+      Result := TEd25519Signer.Create() as IEd25519Signer;
+    TEd25519.TEd25519Algorithm.Ed25519ctx:
+      Result := TEd25519CtxSigner.Create(context) as IEd25519CtxSigner;
+    TEd25519.TEd25519Algorithm.Ed25519ph:
+      Result := TEd25519PhSigner.Create(context) as IEd25519PhSigner;
+  else
+    begin
+      raise EArgumentCryptoLibException.Create('algorithm');
+    end;
+  end;
+end;
+
+procedure TTestEd25519HigherLevel.DoEd25519Test(id: Int32;
+  algorithm: TEd25519SignerAlgorithm; const sk, pk, msg, sig: String);
+var
+  LSk, LPk, LMsg, LSig, LResultSig, LKey: TCryptoLibByteArray;
+  LKeyPair: IAsymmetricCipherKeyPair;
+  LIsVerified: Boolean;
+  LSigner: ISigner;
+begin
+  LSk := THex.Decode(sk);
+  LPk := THex.Decode(pk);
+  LMsg := THex.Decode(msg);
+  LSig := THex.Decode(sig);
+  LKeyPair := ReconstructEd25519KeyPair(algorithm, LSk, LPk);
+  LSigner := CreateCustomSigner(algorithm);
+
+  case algorithm of
+    TTestEd25519HigherLevel.TEd25519SignerAlgorithm.Ed25519:
+      begin
+        LKey := (LKeyPair.Private as IEd25519PrivateKeyParameters).GetEncoded();
+        if not TArrayUtils.AreEqual(LKey, System.Copy(LSk, 0, 32)) then
+        begin
+          Fail(Format
+            ('Test with Id %d Failed on PrivateKey Reconstruction Comparison, Expected "%s" but got "%s"',
+            [id, THex.Encode(LSk), THex.Encode(LKey)]));
+        end;
+
+        LKey := (LKeyPair.Public as IEd25519PublicKeyParameters).GetEncoded();
+        if not TArrayUtils.AreEqual(LKey, System.Copy(LPk, 0, 64)) then
+        begin
+          Fail(Format
+            ('Test with Id %d Failed on PublicKey Reconstruction Comparison, Expected "%s" but got "%s"',
+            [id, THex.Encode(LPk), THex.Encode(LKey)]));
+        end;
+      end;
+    TTestEd25519HigherLevel.TEd25519SignerAlgorithm.Ed25519Blake2B:
+      begin
+        LKey := (LKeyPair.Private as IEd25519Blake2BPrivateKeyParameters)
+          .GetEncoded();
+        if not TArrayUtils.AreEqual(LKey, System.Copy(LSk, 0, 32)) then
+        begin
+          Fail(Format
+            ('Test with Id %d Failed on PrivateKey Reconstruction Comparison, Expected "%s" but got "%s"',
+            [id, THex.Encode(LSk), THex.Encode(LKey)]));
+        end;
+
+        LKey := (LKeyPair.Public as IEd25519Blake2BPublicKeyParameters)
+          .GetEncoded();
+        if not TArrayUtils.AreEqual(LKey, System.Copy(LPk, 0, 64)) then
+        begin
+          Fail(Format
+            ('Test with Id %d Failed on PublicKey Reconstruction Comparison, Expected "%s" but got "%s"',
+            [id, THex.Encode(LPk), THex.Encode(LKey)]));
+        end;
+      end
+  else
+    begin
+      raise EArgumentCryptoLibException.Create('algorithm');
+    end;
+
+  end;
+
+  LSigner.Init(True, LKeyPair.Private);
+  LSigner.BlockUpdate(LMsg, 0, System.length(LMsg));
+  LResultSig := LSigner.GenerateSignature();
+
+  if not TArrayUtils.AreEqual(LResultSig, System.Copy(LSig, 0, 64)) then
+  begin
+    Fail(Format
+      ('Test with Id %d Failed on Signature Comparison, Expected "%s" but got "%s"',
+      [id, THex.Encode(LSig), THex.Encode(LResultSig)]));
+  end;
+
+  LSigner.Init(False, LKeyPair.Public);
+  LSigner.BlockUpdate(LMsg, 0, System.length(LMsg));
+  LIsVerified := LSigner.VerifySignature(LResultSig);
+
+  if not LIsVerified then
+  begin
+    Fail(Format('Test with Id %d Failed on Verifying "%s" Signature',
+      [id, THex.Encode(LResultSig)]));
+  end;
+end;
+
+procedure TTestEd25519HigherLevel.DoTestConsistency
+  (algorithm: TEd25519.TEd25519Algorithm; const context: TCryptoLibByteArray);
+var
+  kpg: IEd25519KeyPairGenerator;
+  kp: IAsymmetricCipherKeyPair;
+  privateKey: IEd25519PrivateKeyParameters;
+  publicKey: IEd25519PublicKeyParameters;
+  msg, signature, wrongLengthSignature: TCryptoLibByteArray;
+  Signer, verifier: ISigner;
+  shouldVerify, shouldNotVerify: Boolean;
+  algorithmName: String;
+  tempRand: Int32;
+begin
+  kpg := TEd25519KeyPairGenerator.Create();
+  kpg.Init(TEd25519KeyGenerationParameters.Create(FRandom)
+    as IEd25519KeyGenerationParameters);
+
+  kp := kpg.GenerateKeyPair();
+  privateKey := kp.Private as IEd25519PrivateKeyParameters;
+  publicKey := kp.Public as IEd25519PublicKeyParameters;
+
+  System.SetLength(msg, FRandom.NextInt32 and 255);
+  FRandom.NextBytes(msg);
+
+  Signer := CreateSigner(algorithm, context);
+  Signer.Init(True, privateKey);
+  Signer.BlockUpdate(msg, 0, System.length(msg));
+  signature := Signer.GenerateSignature();
+
+  verifier := CreateSigner(algorithm, context);
+  verifier.Init(False, publicKey);
+  verifier.BlockUpdate(msg, 0, System.length(msg));
+  shouldVerify := verifier.VerifySignature(signature);
+
+  algorithmName := GetEnumName(TypeInfo(TEd25519.TEd25519Algorithm),
+    Ord(algorithm));
+
+  if (not shouldVerify) then
+  begin
+    Fail(Format('Ed25519 (%s) signature failed to verify', [algorithmName]));
+  end;
+
+  wrongLengthSignature := TArrayUtils.Prepend(signature, Byte($00));
+
+  verifier.Init(False, publicKey);
+  verifier.BlockUpdate(msg, 0, System.length(msg));
+  shouldNotVerify := verifier.VerifySignature(wrongLengthSignature);
+
+  if (shouldNotVerify) then
+  begin
+    Fail(Format('Ed25519 (%s) wrong length signature incorrectly verified',
+      [algorithmName]));
+  end;
+
+  tempRand := FRandom.Next();
+  signature[tempRand mod System.length(signature)] :=
+    signature[tempRand mod System.length(signature)
+    ] xor Byte(1 shl (FRandom.NextInt32 and 7));
+
+  verifier.Init(False, publicKey);
+  verifier.BlockUpdate(msg, 0, System.length(msg));
+  shouldNotVerify := verifier.VerifySignature(signature);
+
+  if (shouldNotVerify) then
+  begin
+    Fail(Format('Ed25519 (%s) bad signature incorrectly verified',
+      [algorithmName]));
+  end;
+end;
+
+function TTestEd25519HigherLevel.RandomContext(length: Int32)
+  : TCryptoLibByteArray;
+begin
+  System.SetLength(Result, length);
+  FRandom.NextBytes(Result);
+end;
+
+function TTestEd25519HigherLevel.ReconstructEd25519KeyPair
+  (algorithm: TEd25519SignerAlgorithm; const sk, pk: TCryptoLibByteArray)
+  : IAsymmetricCipherKeyPair;
+begin
+  case algorithm of
+    TTestEd25519HigherLevel.TEd25519SignerAlgorithm.Ed25519:
+      begin
+        Result := TAsymmetricCipherKeyPair.Create
+          (TEd25519PublicKeyParameters.Create(pk, 0)
+          as IEd25519PublicKeyParameters,
+          TEd25519PrivateKeyParameters.Create(sk, 0)
+          as IEd25519PrivateKeyParameters);
+      end;
+    TTestEd25519HigherLevel.TEd25519SignerAlgorithm.Ed25519Blake2B:
+      begin
+        Result := TAsymmetricCipherKeyPair.Create
+          (TEd25519Blake2BPublicKeyParameters.Create(pk, 0)
+          as IEd25519Blake2BPublicKeyParameters,
+          TEd25519Blake2BPrivateKeyParameters.Create(sk, 0)
+          as IEd25519Blake2BPrivateKeyParameters);
+      end
+  else
+    begin
+      raise EArgumentCryptoLibException.Create('algorithm');
+    end;
+  end;
+end;
+
+procedure TTestEd25519HigherLevel.SetUp;
+begin
+  inherited;
+  FRandom := TSecureRandom.Create();
+end;
+
+procedure TTestEd25519HigherLevel.TearDown;
+begin
+  inherited;
+
+end;
+
+procedure TTestEd25519HigherLevel.TestConsistency;
+var
+  i: Int32;
+  context: TCryptoLibByteArray;
+begin
+  i := 0;
+  while i < 10 do
+  begin
+    DoTestConsistency(TEd25519.TEd25519Algorithm.Ed25519, Nil);
+
+    context := RandomContext(FRandom.NextInt32 and 255);
+    DoTestConsistency(TEd25519.TEd25519Algorithm.Ed25519ctx, context);
+    DoTestConsistency(TEd25519.TEd25519Algorithm.Ed25519ph, context);
+    System.Inc(i);
+  end;
+end;
+
+procedure TTestEd25519HigherLevel.TestEd25519;
+begin
+
+  // TEd25519SignerAlgorithm.Ed25519
+
+  DoEd25519Test(1, TEd25519SignerAlgorithm.Ed25519,
+    '9d61b19deffd5a60ba844af492ec2cc44449c5697b326919703bac031cae7f60d75a980182b10ab7d54bfed3c964073a0ee172f3daa62325af021a68f707511a',
+    'd75a980182b10ab7d54bfed3c964073a0ee172f3daa62325af021a68f707511a', '',
+    'e5564300c360ac729086e2cc806e828a84877f1eb8e5d974d873e065224901555fb8821590a33bacc61e39701cf9b46bd25bf5f0595bbe24655141438e7a100b');
+
+  DoEd25519Test(2, TEd25519SignerAlgorithm.Ed25519,
+    '4ccd089b28ff96da9db6c346ec114e0f5b8a319f35aba624da8cf6ed4fb8a6fb3d4017c3e843895a92b70aa74d1b7ebc9c982ccf2ec4968cc0cd55f12af4660c',
+    '3d4017c3e843895a92b70aa74d1b7ebc9c982ccf2ec4968cc0cd55f12af4660c', '72',
+    '92a009a9f0d4cab8720e820b5f642540a2b27b5416503f8fb3762223ebdb69da085ac1e43e15996e458f3613d0f11d8c387b2eaeb4302aeeb00d291612bb0c0072');
+
+  DoEd25519Test(3, TEd25519SignerAlgorithm.Ed25519,
+    'c5aa8df43f9f837bedb7442f31dcb7b166d38535076f094b85ce3a2e0b4458f7fc51cd8e6218a1a38da47ed00230f0580816ed13ba3303ac5deb911548908025',
+    'fc51cd8e6218a1a38da47ed00230f0580816ed13ba3303ac5deb911548908025', 'af82',
+    '6291d657deec24024827e69c3abe01a30ce548a284743a445e3680d7db5ac3ac18ff9b538d16f290ae67f760984dc6594a7c15e9716ed28dc027beceea1ec40aaf82');
+
+  DoEd25519Test(4, TEd25519SignerAlgorithm.Ed25519,
+    '0d4a05b07352a5436e180356da0ae6efa0345ff7fb1572575772e8005ed978e9e61a185bcef2613a6c7cb79763ce945d3b245d76114dd440bcf5f2dc1aa57057',
+    'e61a185bcef2613a6c7cb79763ce945d3b245d76114dd440bcf5f2dc1aa57057',
+    'cbc77b', 'd9868d52c2bebce5f3fa5a79891970f309cb6591e3e1702a70276fa97c24b3a8e58606c38c9758529da50ee31b8219cba45271c689afa60b0ea26c99db19b00ccbc77b');
+
+  DoEd25519Test(5, TEd25519SignerAlgorithm.Ed25519,
+    '6df9340c138cc188b5fe4464ebaa3f7fc206a2d55c3434707e74c9fc04e20ebbc0dac102c4533186e25dc43128472353eaabdb878b152aeb8e001f92d90233a7',
+    'c0dac102c4533186e25dc43128472353eaabdb878b152aeb8e001f92d90233a7',
+    '5f4c8989',
+    '124f6fc6b0d100842769e71bd530664d888df8507df6c56dedfdb509aeb93416e26b918d38aa06305df3095697c18b2aa832eaa52edc0ae49fbae5a85e150c075f4c8989');
+
+  // TEd25519SignerAlgorithm.Ed25519Blake2B
+
+  DoEd25519Test(6, TEd25519SignerAlgorithm.Ed25519Blake2B,
+    '9d61b19deffd5a60ba844af492ec2cc44449c5697b326919703bac031cae7f60',
+    '78e65bf30f893d32fc57ef051c341bdede242544fc2a2112f0fa2c7afdebc02f', '',
+    '99a523bd4616c8161144d6a99d3c32400cb4a326f4d79e307340f6afa11750a0085d7d84626bc9e4b153fc0e396d15ce44c39bae4533804db1fe5b52f2b1b805');
+
+  DoEd25519Test(7, TEd25519SignerAlgorithm.Ed25519Blake2B,
+    '4ccd089b28ff96da9db6c346ec114e0f5b8a319f35aba624da8cf6ed4fb8a6fb',
+    '5e71392d91e6a58fedeb0850364f56cd158a60447557d7890389c9b3d4576d4d', '72',
+    '6da75e15b5707f4de5a153c48a5d839fb85074c38aeb6285977f03a13977597f976069fdb903f183474aaa5ed0cfe878ba8ef868c5e47ca3f96ccfb3a89b2a0672');
+
+  DoEd25519Test(8, TEd25519SignerAlgorithm.Ed25519Blake2B,
+    'c5aa8df43f9f837bedb7442f31dcb7b166d38535076f094b85ce3a2e0b4458f7',
+    '8d53ca70f0eab23b9178345785fcdb69ed6723f8148f7e339e88653700b718da', 'af82',
+    '7cc3c13852bd12abf3ce4ca8ca2836cbf86da96c4634c50df3fb80dc809e29db0e109c361353407c1236a904f636868aa33977a99d3f844598db1538b4295203af82');
+
+  DoEd25519Test(9, TEd25519SignerAlgorithm.Ed25519Blake2B,
+    '0d4a05b07352a5436e180356da0ae6efa0345ff7fb1572575772e8005ed978e9',
+    '0c6989f1abebe219db9d1e2cb8b0c602b191828ef7238f8e6dbff8a506802c09',
+    'cbc77b', '7fb2c11db736d16ebd07a653463dc8739d3315f89f61a66715e41528cb32b7689393f5af8a66c9c7336e209e6b187259fe266f7941a435fecb8cd7a7fc759400cbc77b');
+
+  DoEd25519Test(10, TEd25519SignerAlgorithm.Ed25519Blake2B,
+    '6df9340c138cc188b5fe4464ebaa3f7fc206a2d55c3434707e74c9fc04e20ebb',
+    'ce99a0d41b2c1bdf593cfe41b0bf38f40ab77a804a71138188cc879b59869d90',
+    '5f4c8989',
+    'e09625735d184975409020659f3c0b07f036a19a7e7aa2100964cef577806e26125d1437577d2d3286c29df871797cac3fc0cdecbbeca616030cfcc6711db6065f4c8989');
+end;
+
+initialization
+
+// Register any test cases with the test runner
+
+{$IFDEF FPC}
+// RegisterTest(TTestEd25519HigherLevel);
+{$ELSE}
+  RegisterTest(TTestEd25519HigherLevel.Suite);
+{$ENDIF FPC}
+
+end.

+ 66 - 60
CryptoLib.Tests/src/Others/NamedCurveTests.pas

@@ -32,10 +32,13 @@ uses
 {$ELSE}
   TestFramework,
 {$ENDIF FPC}
+  ClpBigInteger,
   ClpSecureRandom,
   ClpISecureRandom,
   ClpISigner,
+  ClpIBasicAgreement,
   ClpSecNamedCurves,
+  ClpTeleTrusTNamedCurves,
   ClpIX9ECParameters,
   ClpECDomainParameters,
   ClpECNamedCurveTable,
@@ -48,6 +51,8 @@ uses
   ClpIAsymmetricCipherKeyPairGenerator,
   ClpIAsymmetricCipherKeyPair,
   ClpIECKeyGenerationParameters,
+  ClpGeneratorUtilities,
+  ClpAgreementUtilities,
   ClpConverters,
   ClpCryptoLibTypes;
 
@@ -65,8 +70,8 @@ type
   TTestNamedCurve = class(TCryptoLibTestCase)
   private
     function GetCurveParameters(const name: String): IECDomainParameters;
-    procedure doTestECDsa(const name: String);
-    // procedure doTestECGost(const name: String);
+    procedure DoTestECDsa(const name: String);
+    procedure DoTestCurve(const name: String);
 
   protected
     procedure SetUp; override;
@@ -79,7 +84,7 @@ implementation
 
 { TTestNamedCurve }
 
-procedure TTestNamedCurve.doTestECDsa(const name: String);
+procedure TTestNamedCurve.DoTestECDsa(const name: String);
 var
   ecSpec: IECDomainParameters;
   g: IAsymmetricCipherKeyPairGenerator;
@@ -114,61 +119,55 @@ begin
 
   if (not sgr.VerifySignature(sigBytes)) then
   begin
-    Fail(name + ' verification failed');
+    Fail(Format('%s verification failed', [name]));
   end;
 end;
 
-// procedure TTestNamedCurve.doTestECGost(const name: String);
-// var
-// sgr: ISigner;
-// keyAlgorithm: String;
-// ecSpec: IECDomainParameters;
-// g: IAsymmetricCipherKeyPairGenerator;
-// pair: IAsymmetricCipherKeyPair;
-// sKey, vKey: IAsymmetricKeyParameter;
-// &message, sigBytes: TCryptoLibByteArray;
-// begin
-// if System.Pos('Tc26-Gost-3410', name) > 0 then
-// begin
-// // TODO Implement ECGOST3410-2012 in SignerUtilies/GeneratorUtilities etc.
-// // Current test cases don't work for GOST34.10 2012
-// Exit;
-// end
-// else
-// begin
-// keyAlgorithm := 'ECGOST3410';
-//
-// sgr := TSignerUtilities.GetSigner('ECGOST3410');
-// end;
-//
-// ecSpec := GetCurveParameters(name);
-//
-// g := TECKeyPairGenerator.Create(keyAlgorithm);
-//
-// g.Init(TECKeyGenerationParameters.Create(ecSpec, TSecureRandom.Create() as ISecureRandom) as IECKeyGenerationParameters);
-//
-// pair := g.GenerateKeyPair();
-// sKey := pair.Private;
-// vKey := pair.Public;
-//
-// sgr.Init(true, sKey);
-//
-// &message := TConverters.ConvertStringToBytes('abc', TEncoding.UTF8);
-//
-// sgr.BlockUpdate(&message, 0, System.Length(&message));
-//
-// sigBytes := sgr.GenerateSignature();
-//
-// sgr.Init(false, vKey);
-//
-// sgr.BlockUpdate(&message, 0, System.Length(&message));
-//
-// if (not sgr.VerifySignature(sigBytes)) then
-// begin
-// Fail(name + ' verification failed');
-// end;
-//
-// end;
+procedure TTestNamedCurve.DoTestCurve(const name: String);
+var
+  ecSpec: IECDomainParameters;
+  g: IAsymmetricCipherKeyPairGenerator;
+  aKeyPair, bKeyPair: IAsymmetricCipherKeyPair;
+  aKeyAgree, bKeyAgree: IBasicAgreement;
+  k1, k2: TBigInteger;
+begin
+  ecSpec := GetCurveParameters(name);
+
+  g := TGeneratorUtilities.GetKeyPairGenerator('ECDH');
+
+  g.Init(TECKeyGenerationParameters.Create(ecSpec, TSecureRandom.Create()
+    as ISecureRandom) as IECKeyGenerationParameters);
+
+  //
+  // a side
+  //
+  aKeyPair := g.GenerateKeyPair();
+
+  aKeyAgree := TAgreementUtilities.GetBasicAgreement('ECDHC');
+
+  aKeyAgree.Init(aKeyPair.Private);
+
+  //
+  // b side
+  //
+  bKeyPair := g.GenerateKeyPair();
+
+  bKeyAgree := TAgreementUtilities.GetBasicAgreement('ECDHC');
+
+  bKeyAgree.Init(bKeyPair.Private);
+
+  //
+  // agreement
+  //
+
+  k1 := aKeyAgree.CalculateAgreement(bKeyPair.Public);
+  k2 := bKeyAgree.CalculateAgreement(aKeyPair.Public);
+
+  if (not k1.Equals(k2)) then
+  begin
+    Fail('2-way test failed');
+  end;
+end;
 
 function TTestNamedCurve.GetCurveParameters(const name: String)
   : IECDomainParameters;
@@ -211,15 +210,22 @@ procedure TTestNamedCurve.TestPerform;
 var
   name: string;
 begin
+  DoTestCurve('sect571r1'); // sec
+  DoTestCurve('secp224r1');
+  DoTestCurve('B-409'); // nist
+  DoTestCurve('P-521');
+  DoTestCurve('brainpoolp160r1'); // TeleTrusT
+
   for name in TSecNamedCurves.Names do
   begin
-    doTestECDsa(name);
+    DoTestECDsa(name);
+  end;
+
+  for name in TTeleTrusTNamedCurves.Names do
+  begin
+    DoTestECDsa(name);
   end;
 
-  // for name in TECGost3410NamedCurves.Names do
-  // begin
-  // doTestECGost(name);
-  // end;
 end;
 
 initialization

+ 171 - 0
CryptoLib.Tests/src/Others/ShortenedDigestTests.pas

@@ -0,0 +1,171 @@
+{ *********************************************************************************** }
+{ *                              CryptoLib Library                                  * }
+{ *                Copyright (c) 2018 - 20XX Ugochukwu Mmaduekwe                    * }
+{ *                 Github Repository <https://github.com/Xor-el>                   * }
+
+{ *  Distributed under the MIT software license, see the accompanying file LICENSE  * }
+{ *          or visit http://www.opensource.org/licenses/mit-license.php.           * }
+
+{ *                              Acknowledgements:                                  * }
+{ *                                                                                 * }
+{ *      Thanks to Sphere 10 Software (http://www.sphere10.com/) for sponsoring     * }
+{ *                           development of this library                           * }
+
+{ * ******************************************************************************* * }
+
+(* &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&& *)
+
+unit ShortenedDigestTests;
+
+interface
+
+{$IFDEF FPC}
+{$MODE DELPHI}
+{$ENDIF FPC}
+
+uses
+  SysUtils,
+{$IFDEF FPC}
+  fpcunit,
+  testregistry,
+{$ELSE}
+  TestFramework,
+{$ENDIF FPC}
+  ClpIDigest,
+  ClpIShortenedDigest,
+  ClpShortenedDigest,
+  ClpDigestUtilities,
+  ClpArrayUtils,
+  ClpCryptoLibTypes;
+
+type
+
+  TCryptoLibTestCase = class abstract(TTestCase)
+
+  end;
+
+type
+
+  TTestShortenedDigest = class(TCryptoLibTestCase)
+
+  private
+    procedure DoTestShortenedDigest();
+
+  protected
+    procedure SetUp; override;
+    procedure TearDown; override;
+  published
+    procedure TestShortenedDigest();
+
+  end;
+
+implementation
+
+{ TTestShortenedDigest }
+
+procedure TTestShortenedDigest.DoTestShortenedDigest;
+var
+  d: IDigest;
+  sd: IShortenedDigest;
+  temp, temp2: TCryptoLibByteArray;
+begin
+  d := TDigestUtilities.GetDigest('SHA-1');
+  sd := TShortenedDigest.Create(TDigestUtilities.GetDigest('SHA-1'), 10);
+
+  if (sd.GetDigestSize() <> 10) then
+  begin
+    Fail('size check wrong for SHA-1');
+  end;
+
+  if (sd.GetByteLength() <> d.GetByteLength()) then
+  begin
+    Fail('byte length check wrong for SHA-1');
+  end;
+
+  //
+  // check output fits
+  //
+  System.SetLength(temp, 10);
+  System.SetLength(temp2, 10);
+  sd.DoFinal(temp, 0);
+  sd.DoFinal(temp2, 0);
+
+  CheckTrue(TArrayUtils.AreEqual(temp, temp2),
+    Format('DoFinal(temp, 0) <> temp := DoFinal() %s', [sd.AlgorithmName]));
+
+  d := TDigestUtilities.GetDigest('SHA-512');
+  sd := TShortenedDigest.Create(TDigestUtilities.GetDigest('SHA-512'), 20);
+
+  if (sd.GetDigestSize() <> 20) then
+  begin
+    Fail('size check wrong for SHA-512');
+  end;
+
+  if (sd.GetByteLength() <> d.GetByteLength()) then
+  begin
+    Fail('byte length check wrong for SHA-512');
+  end;
+
+  //
+  // check output fits
+  //
+  System.SetLength(temp, 20);
+  System.SetLength(temp2, 20);
+  sd.DoFinal(temp, 0);
+  sd.DoFinal(temp2, 0);
+
+  CheckTrue(TArrayUtils.AreEqual(temp, temp2),
+    Format('DoFinal(temp, 0) <> temp := DoFinal() %s', [sd.AlgorithmName]));
+
+  try
+    TShortenedDigest.Create(Nil, 20);
+    Fail('Nil parameter not caught');
+  except
+    on e: EArgumentNilCryptoLibException do
+    begin
+      // expected
+    end;
+
+  end;
+
+  try
+    TShortenedDigest.Create(TDigestUtilities.GetDigest('SHA-1'), 50);
+    Fail('short digest not caught');
+  except
+    on e: EArgumentCryptoLibException do
+    begin
+      // expected
+    end;
+
+  end;
+
+end;
+
+procedure TTestShortenedDigest.SetUp;
+begin
+  inherited;
+
+end;
+
+procedure TTestShortenedDigest.TearDown;
+begin
+  inherited;
+
+end;
+
+procedure TTestShortenedDigest.TestShortenedDigest;
+begin
+  DoTestShortenedDigest();
+end;
+
+initialization
+
+// Register any test cases with the test runner
+
+{$IFDEF FPC}
+  RegisterTest(TTestShortenedDigest);
+{$ELSE}
+  RegisterTest(TTestShortenedDigest.Suite);
+{$ENDIF FPC}
+
+end.

+ 23 - 1
CryptoLib.Tests/src/Others/SignerUtilitiesTests.pas

@@ -40,6 +40,7 @@ uses
   ClpIRandom,
   ClpSignerUtilities,
   ClpSecureRandom,
+  ClpISecureRandom,
   ClpECDomainParameters,
   ClpICipherParameters,
   ClpIECDomainParameters,
@@ -53,7 +54,12 @@ uses
   ClpIDsaPublicKeyParameters,
   ClpDsaParameters,
   ClpDsaPrivateKeyParameters,
-  ClpDsaPublicKeyParameters;
+  ClpDsaPublicKeyParameters,
+  ClpIAsymmetricCipherKeyPairGenerator,
+  ClpEd25519KeyGenerationParameters,
+  ClpIEd25519KeyGenerationParameters,
+  ClpIAsymmetricCipherKeyPair,
+  ClpGeneratorUtilities;
 
 type
 
@@ -76,6 +82,8 @@ type
     Fpara: IDsaParameters;
     FdsaPriv: IDsaPrivateKeyParameters;
     FdsaPub: IDsaPublicKeyParameters;
+    Fed25519Kpg: IAsymmetricCipherKeyPairGenerator;
+    Fed25519Pair: IAsymmetricCipherKeyPair;
 
   protected
     procedure SetUp; override;
@@ -154,6 +162,15 @@ begin
   FdsaPriv := TDsaPrivateKeyParameters.Create(FDsaPrivateX, Fpara);
   FdsaPub := TDsaPublicKeyParameters.Create(FDSAPublicY, Fpara);
 
+  //
+  // EdDSA parameters
+  //
+
+  Fed25519Kpg := TGeneratorUtilities.GetKeyPairGenerator('Ed25519');
+  Fed25519Kpg.Init(TEd25519KeyGenerationParameters.Create(TSecureRandom.Create()
+    as ISecureRandom) as IEd25519KeyGenerationParameters);
+  Fed25519Pair := Fed25519Kpg.GenerateKeyPair();
+
 end;
 
 procedure TTestSignerUtilities.TearDown;
@@ -211,6 +228,11 @@ begin
       signParams := FdsaPriv;
       verifyParams := FdsaPub;
     end
+    else if (cipherName = 'ED25519') then
+    begin
+      signParams := Fed25519Pair.Private;
+      verifyParams := Fed25519Pair.Public;
+    end
     else
     begin
       Fail('Unknown algorithm encountered: ' + cipherName);

+ 136 - 0
CryptoLib.Tests/src/Others/X25519HigherLevelTests.pas

@@ -0,0 +1,136 @@
+{ *********************************************************************************** }
+{ *                              CryptoLib Library                                  * }
+{ *                Copyright (c) 2018 - 20XX Ugochukwu Mmaduekwe                    * }
+{ *                 Github Repository <https://github.com/Xor-el>                   * }
+
+{ *  Distributed under the MIT software license, see the accompanying file LICENSE  * }
+{ *          or visit http://www.opensource.org/licenses/mit-license.php.           * }
+
+{ *                              Acknowledgements:                                  * }
+{ *                                                                                 * }
+{ *      Thanks to Sphere 10 Software (http://www.sphere10.com/) for sponsoring     * }
+{ *                           development of this library                           * }
+
+{ * ******************************************************************************* * }
+
+(* &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&& *)
+
+unit X25519HigherLevelTests;
+
+interface
+
+{$IFDEF FPC}
+{$MODE DELPHI}
+{$ENDIF FPC}
+
+uses
+{$IFDEF FPC}
+  fpcunit,
+  testregistry,
+{$ELSE}
+  TestFramework,
+{$ENDIF FPC}
+  ClpSecureRandom,
+  ClpISecureRandom,
+  ClpArrayUtils,
+  ClpX25519Agreement,
+  ClpIX25519Agreement,
+  ClpIAsymmetricCipherKeyPair,
+  ClpX25519KeyPairGenerator,
+  ClpIX25519KeyPairGenerator,
+  ClpX25519KeyGenerationParameters,
+  ClpIX25519KeyGenerationParameters,
+  ClpIAsymmetricCipherKeyPairGenerator,
+  ClpCryptoLibTypes;
+
+type
+
+  TCryptoLibTestCase = class abstract(TTestCase)
+
+  end;
+
+type
+
+  TTestX25519HigherLevel = class(TCryptoLibTestCase)
+  private
+  var
+    FRandom: ISecureRandom;
+
+    procedure DoTestAgreement();
+  protected
+    procedure SetUp; override;
+    procedure TearDown; override;
+  published
+    procedure TestAgreement();
+
+  end;
+
+implementation
+
+{ TTestX25519HigherLevel }
+
+procedure TTestX25519HigherLevel.DoTestAgreement;
+var
+  kpGen: IAsymmetricCipherKeyPairGenerator;
+  kpA, kpB: IAsymmetricCipherKeyPair;
+  agreeA, agreeB: IX25519Agreement;
+  secretA, secretB: TCryptoLibByteArray;
+begin
+  kpGen := TX25519KeyPairGenerator.Create() as IX25519KeyPairGenerator;
+  kpGen.Init(TX25519KeyGenerationParameters.Create(FRandom)
+    as IX25519KeyGenerationParameters);
+
+  kpA := kpGen.GenerateKeyPair();
+  kpB := kpGen.GenerateKeyPair();
+
+  agreeA := TX25519Agreement.Create();
+  agreeA.Init(kpA.Private);
+  System.SetLength(secretA, agreeA.AgreementSize);
+  agreeA.CalculateAgreement(kpB.Public, secretA, 0);
+
+  agreeB := TX25519Agreement.Create();
+  agreeB.Init(kpB.Private);
+  System.SetLength(secretB, agreeB.AgreementSize);
+  agreeB.CalculateAgreement(kpA.Public, secretB, 0);
+
+  if (not TArrayUtils.AreEqual(secretA, secretB)) then
+  begin
+    Fail('X25519 agreement failed');
+  end;
+end;
+
+procedure TTestX25519HigherLevel.SetUp;
+begin
+  inherited;
+  FRandom := TSecureRandom.Create();
+end;
+
+procedure TTestX25519HigherLevel.TearDown;
+begin
+  inherited;
+
+end;
+
+procedure TTestX25519HigherLevel.TestAgreement;
+var
+  i: Int32;
+begin
+  i := 0;
+  while i < 10 do
+  begin
+    DoTestAgreement();
+    System.Inc(i);
+  end;
+end;
+
+initialization
+
+// Register any test cases with the test runner
+
+{$IFDEF FPC}
+// RegisterTest(TTestX25519HigherLevel);
+{$ELSE}
+  RegisterTest(TTestX25519HigherLevel.Suite);
+{$ENDIF FPC}
+
+end.

+ 280 - 0
CryptoLib.Tests/src/Security/DigestUtilitiesTests.pas

@@ -0,0 +1,280 @@
+{ *********************************************************************************** }
+{ *                              CryptoLib Library                                  * }
+{ *                Copyright (c) 2018 - 20XX Ugochukwu Mmaduekwe                    * }
+{ *                 Github Repository <https://github.com/Xor-el>                   * }
+
+{ *  Distributed under the MIT software license, see the accompanying file LICENSE  * }
+{ *          or visit http://www.opensource.org/licenses/mit-license.php.           * }
+
+{ *                              Acknowledgements:                                  * }
+{ *                                                                                 * }
+{ *      Thanks to Sphere 10 Software (http://www.sphere10.com/) for sponsoring     * }
+{ *                           development of this library                           * }
+
+{ * ******************************************************************************* * }
+
+(* &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&& *)
+
+unit DigestUtilitiesTests;
+
+interface
+
+{$IFDEF FPC}
+{$MODE DELPHI}
+{$ENDIF FPC}
+
+uses
+  SysUtils,
+{$IFDEF FPC}
+  fpcunit,
+  testregistry,
+{$ELSE}
+  TestFramework,
+{$ENDIF FPC}
+  HlpIHashInfo,
+  HlpHashFactory,
+  ClpIDigest,
+  ClpDigest,
+  ClpDigestUtilities,
+  ClpArrayUtils,
+  ClpCryptoLibTypes;
+
+type
+
+  TCryptoLibTestCase = class abstract(TTestCase)
+
+  end;
+
+type
+
+  TTestDigestUtilities = class(TCryptoLibTestCase)
+  private
+  var
+    FTestBytes: TCryptoLibByteArray;
+
+    function MakeTestPlainDigest(const digest: IDigest): TCryptoLibByteArray;
+    procedure CheckPlainDigestAlgorithm(const name: String;
+      const digest: IDigest);
+
+    function MakeTestXofDigest(const digest: IDigest; count: Int32)
+      : TCryptoLibByteArray;
+    procedure CheckXofDigestAlgorithm(const name: String;
+      const digest: IDigest);
+
+  protected
+    procedure SetUp; override;
+    procedure TearDown; override;
+  published
+    procedure TestAlgorithms();
+
+  end;
+
+implementation
+
+{ TTestDigestUtilities }
+
+procedure TTestDigestUtilities.SetUp;
+begin
+  inherited;
+  System.SetLength(FTestBytes, 100);
+end;
+
+procedure TTestDigestUtilities.TearDown;
+begin
+  FTestBytes := Nil;
+  inherited;
+end;
+
+function TTestDigestUtilities.MakeTestXofDigest(const digest: IDigest;
+  count: Int32): TCryptoLibByteArray;
+begin
+  System.SetLength(Result, count);
+  digest.BlockUpdate(FTestBytes, 0, System.Length(FTestBytes));
+  digest.DoFinal(Result, 0);
+end;
+
+function TTestDigestUtilities.MakeTestPlainDigest(const digest: IDigest)
+  : TCryptoLibByteArray;
+var
+  i: Int32;
+begin
+  for i := 0 to System.Pred(digest.GetDigestSize()) do
+  begin
+    digest.Update(Byte(i));
+  end;
+
+  digest.BlockUpdate(FTestBytes, 0, System.Length(FTestBytes));
+
+  Result := TDigestUtilities.DoFinal(digest);
+end;
+
+procedure TTestDigestUtilities.CheckXofDigestAlgorithm(const name: String;
+  const digest: IDigest);
+var
+  hash1, hash2: TCryptoLibByteArray;
+  i: Int32;
+begin
+  for i := 1 to 100 do
+  begin
+    hash1 := MakeTestXofDigest(digest, i);
+    hash2 := MakeTestXofDigest(TDigestUtilities.GetDigest(name), i);
+
+    if not TArrayUtils.AreEqual(hash1, hash2) then
+    begin
+      Fail(Format
+        ('%s (%d) at Index %d CheckXofDigestAlgorithm Operation Failed',
+        [name, (digest as IXOF).XOFSizeInBits, i]));
+    end;
+  end;
+end;
+
+procedure TTestDigestUtilities.CheckPlainDigestAlgorithm(const name: String;
+  const digest: IDigest);
+var
+  hash1, hash2: TCryptoLibByteArray;
+begin
+  hash1 := MakeTestPlainDigest(digest);
+  hash2 := MakeTestPlainDigest(TDigestUtilities.GetDigest(name));
+
+  if not TArrayUtils.AreEqual(hash1, hash2) then
+  begin
+    Fail(Format('%s CheckPlainDigestAlgorithm Operation Failed', [name]));
+  end;
+end;
+
+procedure TTestDigestUtilities.TestAlgorithms;
+begin
+  // plain digest test
+  CheckPlainDigestAlgorithm('MD2',
+    TDigest.Create(THashFactory.TCrypto.CreateMD2()) as IDigest);
+
+  CheckPlainDigestAlgorithm('MD4',
+    TDigest.Create(THashFactory.TCrypto.CreateMD4()) as IDigest);
+
+  CheckPlainDigestAlgorithm('MD5',
+    TDigest.Create(THashFactory.TCrypto.CreateMD5()) as IDigest);
+
+  CheckPlainDigestAlgorithm('SHA-1',
+    TDigest.Create(THashFactory.TCrypto.CreateSHA1()) as IDigest);
+
+  CheckPlainDigestAlgorithm('SHA-224',
+    TDigest.Create(THashFactory.TCrypto.CreateSHA2_224()) as IDigest);
+
+  CheckPlainDigestAlgorithm('SHA-256',
+    TDigest.Create(THashFactory.TCrypto.CreateSHA2_256()) as IDigest);
+
+  CheckPlainDigestAlgorithm('SHA-384',
+    TDigest.Create(THashFactory.TCrypto.CreateSHA2_384()) as IDigest);
+
+  CheckPlainDigestAlgorithm('SHA-512',
+    TDigest.Create(THashFactory.TCrypto.CreateSHA2_512()) as IDigest);
+
+  CheckPlainDigestAlgorithm('SHA-512/224',
+    TDigest.Create(THashFactory.TCrypto.CreateSHA2_512_224()) as IDigest);
+
+  CheckPlainDigestAlgorithm('SHA-512/256',
+    TDigest.Create(THashFactory.TCrypto.CreateSHA2_512_256()) as IDigest);
+
+  CheckPlainDigestAlgorithm('KECCAK224',
+    TDigest.Create(THashFactory.TCrypto.CreateKeccak_224()) as IDigest);
+
+  CheckPlainDigestAlgorithm('KECCAK256',
+    TDigest.Create(THashFactory.TCrypto.CreateKeccak_256()) as IDigest);
+
+  CheckPlainDigestAlgorithm('KECCAK288',
+    TDigest.Create(THashFactory.TCrypto.CreateKeccak_288()) as IDigest);
+
+  CheckPlainDigestAlgorithm('KECCAK384',
+    TDigest.Create(THashFactory.TCrypto.CreateKeccak_384()) as IDigest);
+
+  CheckPlainDigestAlgorithm('KECCAK512',
+    TDigest.Create(THashFactory.TCrypto.CreateKeccak_512()) as IDigest);
+
+  CheckPlainDigestAlgorithm('SHA3-224',
+    TDigest.Create(THashFactory.TCrypto.CreateSHA3_224()) as IDigest);
+
+  CheckPlainDigestAlgorithm('SHA3-256',
+    TDigest.Create(THashFactory.TCrypto.CreateSHA3_256()) as IDigest);
+
+  CheckPlainDigestAlgorithm('SHA3-384',
+    TDigest.Create(THashFactory.TCrypto.CreateSHA3_384()) as IDigest);
+
+  CheckPlainDigestAlgorithm('SHA3-512',
+    TDigest.Create(THashFactory.TCrypto.CreateSHA3_512()) as IDigest);
+
+  CheckXofDigestAlgorithm('SHAKE128',
+    TDigest.Create(THashFactory.TXOF.CreateShake_128(128)) as IDigest);
+
+  CheckXofDigestAlgorithm('SHAKE256',
+    TDigest.Create(THashFactory.TXOF.CreateShake_256(256)) as IDigest);
+
+  CheckPlainDigestAlgorithm('RIPEMD128',
+    TDigest.Create(THashFactory.TCrypto.CreateRIPEMD128()) as IDigest);
+
+  CheckPlainDigestAlgorithm('RIPEMD160',
+    TDigest.Create(THashFactory.TCrypto.CreateRIPEMD160()) as IDigest);
+
+  CheckPlainDigestAlgorithm('RIPEMD256',
+    TDigest.Create(THashFactory.TCrypto.CreateRIPEMD256()) as IDigest);
+
+  CheckPlainDigestAlgorithm('RIPEMD320',
+    TDigest.Create(THashFactory.TCrypto.CreateRIPEMD320()) as IDigest);
+
+  CheckPlainDigestAlgorithm('GOST3411',
+    TDigest.Create(THashFactory.TCrypto.CreateGost()) as IDigest);
+
+  CheckPlainDigestAlgorithm('BLAKE2B-160',
+    TDigest.Create(THashFactory.TCrypto.CreateBlake2B_160()) as IDigest);
+
+  CheckPlainDigestAlgorithm('BLAKE2B-256',
+    TDigest.Create(THashFactory.TCrypto.CreateBlake2B_256()) as IDigest);
+
+  CheckPlainDigestAlgorithm('BLAKE2B-384',
+    TDigest.Create(THashFactory.TCrypto.CreateBlake2B_384()) as IDigest);
+
+  CheckPlainDigestAlgorithm('BLAKE2B-512',
+    TDigest.Create(THashFactory.TCrypto.CreateBlake2B_512()) as IDigest);
+
+  CheckPlainDigestAlgorithm('BLAKE2S-128',
+    TDigest.Create(THashFactory.TCrypto.CreateBlake2S_128()) as IDigest);
+
+  CheckPlainDigestAlgorithm('BLAKE2S-160',
+    TDigest.Create(THashFactory.TCrypto.CreateBlake2S_160()) as IDigest);
+
+  CheckPlainDigestAlgorithm('BLAKE2S-224',
+    TDigest.Create(THashFactory.TCrypto.CreateBlake2S_224()) as IDigest);
+
+  CheckPlainDigestAlgorithm('BLAKE2S-256',
+    TDigest.Create(THashFactory.TCrypto.CreateBlake2S_256()) as IDigest);
+
+  CheckPlainDigestAlgorithm('GOST3411-2012-256',
+    TDigest.Create(THashFactory.TCrypto.CreateGOST3411_2012_256()) as IDigest);
+
+  CheckPlainDigestAlgorithm('GOST3411-2012-512',
+    TDigest.Create(THashFactory.TCrypto.CreateGOST3411_2012_512()) as IDigest);
+
+  CheckPlainDigestAlgorithm('Tiger',
+    TDigest.Create(THashFactory.TCrypto.CreateTiger_3_192()) as IDigest);
+
+  CheckPlainDigestAlgorithm('Whirlpool',
+    TDigest.Create(THashFactory.TCrypto.CreateWhirlPool()) as IDigest);
+
+  // Xof test
+  CheckXofDigestAlgorithm('SHAKE128',
+    TDigest.Create(THashFactory.TXOF.CreateShake_128(128)) as IDigest);
+
+  CheckXofDigestAlgorithm('SHAKE256',
+    TDigest.Create(THashFactory.TXOF.CreateShake_256(256)) as IDigest);
+end;
+
+initialization
+
+// Register any test cases with the test runner
+
+{$IFDEF FPC}
+  RegisterTest(TTestDigestUtilities);
+{$ELSE}
+  RegisterTest(TTestDigestUtilities.Suite);
+{$ENDIF FPC}
+
+end.

+ 39 - 0
CryptoLib.Tests/src/Utils/ClpIShortenedDigest.pas

@@ -0,0 +1,39 @@
+{ *********************************************************************************** }
+{ *                              CryptoLib Library                                  * }
+{ *                Copyright (c) 2018 - 20XX Ugochukwu Mmaduekwe                    * }
+{ *                 Github Repository <https://github.com/Xor-el>                   * }
+
+{ *  Distributed under the MIT software license, see the accompanying file LICENSE  * }
+{ *          or visit http://www.opensource.org/licenses/mit-license.php.           * }
+
+{ *                              Acknowledgements:                                  * }
+{ *                                                                                 * }
+{ *      Thanks to Sphere 10 Software (http://www.sphere10.com/) for sponsoring     * }
+{ *                           development of this library                           * }
+
+{ * ******************************************************************************* * }
+
+(* &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&& *)
+
+unit ClpIShortenedDigest;
+
+interface
+
+{$IFDEF FPC}
+{$MODE DELPHI}
+{$ENDIF FPC}
+
+uses
+  ClpIDigest,
+  ClpCryptoLibTypes;
+
+type
+
+  IShortenedDigest = interface(IDigest)
+    ['{E19D250B-CAE0-4959-9211-80853FCF4ADD}']
+
+  end;
+
+implementation
+
+end.

+ 176 - 0
CryptoLib.Tests/src/Utils/ClpShortenedDigest.pas

@@ -0,0 +1,176 @@
+{ *                              CryptoLib Library                                  * }
+{ *                Copyright (c) 2018 - 20XX Ugochukwu Mmaduekwe                    * }
+{ *                 Github Repository <https://github.com/Xor-el>                   * }
+
+{ *  Distributed under the MIT software license, see the accompanying file LICENSE  * }
+{ *          or visit http://www.opensource.org/licenses/mit-license.php.           * }
+
+{ *                              Acknowledgements:                                  * }
+{ *                                                                                 * }
+{ *      Thanks to Sphere 10 Software (http://www.sphere10.com/) for sponsoring     * }
+{ *                           development of this library                           * }
+
+{ * ******************************************************************************* * }
+
+(* &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&& *)
+
+unit ClpShortenedDigest;
+
+interface
+
+{$IFDEF FPC}
+{$MODE DELPHI}
+{$ENDIF FPC}
+
+uses
+  SysUtils,
+  HlpIHash,
+  ClpIDigest,
+  ClpIShortenedDigest,
+  ClpCryptoLibTypes;
+
+resourcestring
+  SBaseDigestNil = 'BaseDigest Nil';
+  SBaseDigestSizeInsufficient =
+    'BaseDigest output not large enough to support length';
+
+type
+
+  /// <summary>
+  /// Wrapper class that reduces the output length of a particular digest to
+  /// only the first n bytes of the digest function.
+  /// </summary>
+  TShortenedDigest = class sealed(TInterfacedObject, IShortenedDigest)
+
+  strict private
+  var
+    FBaseDigest: IDigest;
+    FLength: Int32;
+
+    function GetAlgorithmName: String; inline;
+
+  public
+
+    /// <summary>
+    /// Base constructor.
+    /// </summary>
+    /// <param name="baseDigest">
+    /// underlying digest to use.
+    /// </param>
+    /// <param name="length">
+    /// length in bytes of the output of doFinal.
+    /// </param>
+    /// <exception cref="EArgumentCryptoLibException">
+    /// if length is greater than baseDigest.GetDigestSize().
+    /// </exception>
+    /// <exception cref="ClpCryptoLibTypes|EArgumentNilCryptoLibException">
+    /// if baseDigest is null.
+    /// </exception>
+    constructor Create(const baseDigest: IDigest; length: Int32);
+
+    function GetDigestSize(): Int32;
+
+    function GetByteLength(): Int32;
+
+    function GetUnderlyingIHash: IHash;
+
+    procedure Update(input: Byte);
+
+    procedure BlockUpdate(const input: TCryptoLibByteArray; inOff, len: Int32);
+
+    function DoFinal(const output: TCryptoLibByteArray; outOff: Int32)
+      : Int32; overload;
+    function DoFinal: TCryptoLibByteArray; overload;
+
+    procedure Reset();
+
+    property AlgorithmName: String read GetAlgorithmName;
+
+    function Clone(): IDigest;
+
+  end;
+
+implementation
+
+{ TShortenedDigest }
+
+constructor TShortenedDigest.Create(const baseDigest: IDigest; length: Int32);
+begin
+  if (baseDigest = Nil) then
+  begin
+    raise EArgumentNilCryptoLibException.CreateRes(@SBaseDigestNil);
+  end;
+
+  if (length > baseDigest.GetDigestSize()) then
+  begin
+    raise EArgumentCryptoLibException.CreateRes(@SBaseDigestSizeInsufficient);
+  end;
+
+  Inherited Create();
+  FBaseDigest := baseDigest;
+  FLength := length;
+end;
+
+function TShortenedDigest.GetAlgorithmName: String;
+begin
+  result := Format('%s(%d)', [FBaseDigest.AlgorithmName, FLength * 8]);;
+end;
+
+function TShortenedDigest.GetByteLength: Int32;
+begin
+  result := FBaseDigest.GetByteLength();
+end;
+
+function TShortenedDigest.GetDigestSize: Int32;
+begin
+  result := FLength;
+end;
+
+function TShortenedDigest.GetUnderlyingIHash: IHash;
+begin
+  result := FBaseDigest.GetUnderlyingIHash;
+end;
+
+procedure TShortenedDigest.Update(input: Byte);
+begin
+  FBaseDigest.Update(input);
+end;
+
+procedure TShortenedDigest.BlockUpdate(const input: TCryptoLibByteArray;
+  inOff, len: Int32);
+begin
+  FBaseDigest.BlockUpdate(input, inOff, len);
+end;
+
+function TShortenedDigest.DoFinal(const output: TCryptoLibByteArray;
+  outOff: Int32): Int32;
+var
+  tmp: TCryptoLibByteArray;
+begin
+  System.SetLength(tmp, FBaseDigest.GetDigestSize());
+
+  FBaseDigest.DoFinal(tmp, 0);
+
+  System.Move(tmp[0], output[outOff], FLength * System.SizeOf(Byte));
+
+  result := FLength;
+end;
+
+function TShortenedDigest.DoFinal: TCryptoLibByteArray;
+begin
+  System.SetLength(result, FLength);
+  DoFinal(result, 0);
+end;
+
+procedure TShortenedDigest.Reset;
+begin
+  FBaseDigest.Reset();
+end;
+
+function TShortenedDigest.Clone(): IDigest;
+begin
+  result := (TShortenedDigest.Create(FBaseDigest.Clone(), FLength)
+    as IShortenedDigest) as IDigest;
+end;
+
+end.

+ 4 - 4
CryptoLib/src/Asn1/ClpAsn1Objects.pas

@@ -784,7 +784,7 @@ type
   strict protected
     function GetCount: Int32; virtual;
     function GetParser: IAsn1SequenceParser; virtual;
-    function GetSelf(Index: Integer): IAsn1Encodable; virtual;
+    function GetSelf(Index: Int32): IAsn1Encodable; virtual;
     function GetCurrent(const e: IAsn1Encodable): IAsn1Encodable;
     function Asn1GetHashCode(): Int32; override;
     function Asn1Equals(const asn1Object: IAsn1Object): Boolean; override;
@@ -1179,7 +1179,7 @@ type
   strict protected
     function GetCount: Int32; virtual;
     function GetParser: IAsn1SetParser; inline;
-    function GetSelf(Index: Integer): IAsn1Encodable; virtual;
+    function GetSelf(Index: Int32): IAsn1Encodable; virtual;
     function GetCurrent(const e: IAsn1Encodable): IAsn1Encodable;
     function Asn1GetHashCode(): Int32; override;
     function Asn1Equals(const asn1Object: IAsn1Object): Boolean; override;
@@ -5470,7 +5470,7 @@ begin
   result := TAsn1SequenceParserImpl.Create(Self as IAsn1Sequence);
 end;
 
-function TAsn1Sequence.GetSelf(Index: Integer): IAsn1Encodable;
+function TAsn1Sequence.GetSelf(Index: Int32): IAsn1Encodable;
 begin
   result := FSeq[index];
 end;
@@ -6301,7 +6301,7 @@ begin
   result := TAsn1SetParserImpl.Create(Self as IAsn1Set);
 end;
 
-function TAsn1Set.GetSelf(Index: Integer): IAsn1Encodable;
+function TAsn1Set.GetSelf(Index: Int32): IAsn1Encodable;
 begin
   result := F_set[index];
 end;

+ 2 - 0
CryptoLib/src/Asn1/Edec/ClpEdECObjectIdentifiers.pas

@@ -17,6 +17,8 @@
 
 unit ClpEdECObjectIdentifiers;
 
+{$I ..\..\Include\CryptoLib.inc}
+
 interface
 
 uses

+ 12 - 1
CryptoLib/src/Asn1/Misc/ClpMiscObjectIdentifiers.pas

@@ -37,7 +37,7 @@ type
       Fcryptlib_algorithm_blowfish_CBC, Fcryptlib_algorithm_blowfish_CFB,
       Fcryptlib_algorithm_blowfish_OFB, Fblake2, Fid_blake2b160, Fid_blake2b256,
       Fid_blake2b384, Fid_blake2b512, Fid_blake2s128, Fid_blake2s160,
-      Fid_blake2s224, Fid_blake2s256: IDerObjectIdentifier;
+      Fid_blake2s224, Fid_blake2s256, Fid_scrypt: IDerObjectIdentifier;
 
     class function Getcryptlib: IDerObjectIdentifier; static; inline;
 
@@ -63,6 +63,8 @@ type
     class function Getid_blake2s224: IDerObjectIdentifier; static; inline;
     class function Getid_blake2s256: IDerObjectIdentifier; static; inline;
 
+    class function Getid_scrypt: IDerObjectIdentifier; static; inline;
+
     class constructor MiscObjectIdentifiers();
 
   public
@@ -92,6 +94,8 @@ type
     class property id_blake2s224: IDerObjectIdentifier read Getid_blake2s224;
     class property id_blake2s256: IDerObjectIdentifier read Getid_blake2s256;
 
+    class property id_scrypt: IDerObjectIdentifier read Getid_scrypt;
+
     class procedure Boot(); static;
 
   end;
@@ -180,6 +184,11 @@ begin
   result := Fid_blake2s256;
 end;
 
+class function TMiscObjectIdentifiers.Getid_scrypt: IDerObjectIdentifier;
+begin
+  result := Fid_scrypt;
+end;
+
 class procedure TMiscObjectIdentifiers.Boot;
 begin
 
@@ -213,6 +222,8 @@ begin
     Fid_blake2s224 := blake2.Branch('2.7');
     Fid_blake2s256 := blake2.Branch('2.8');
 
+    Fid_scrypt := TDerObjectIdentifier.Create('1.3.6.1.4.1.11591.4.11');
+
     FIsBooted := True;
   end;
 end;

+ 25 - 10
CryptoLib/src/Asn1/Nist/ClpNistObjectIdentifiers.pas

@@ -35,15 +35,15 @@ type
     FIsBooted: Boolean;
     FNistAlgorithm, FHashAlgs, FSigAlgs, FIdSha256, FIdSha384, FIdSha512,
       FIdSha224, FIdSha512_224, FIdSha512_256, FIdSha3_224, FIdSha3_256,
-      FIdSha3_384, FIdSha3_512, FIdHMacWithSha3_224, FIdHMacWithSha3_256,
-      FIdHMacWithSha3_384, FIdHMacWithSha3_512, FAES, FIdAES128Ecb,
-      FIdAes128Cbc, FIdAes128Ofb, FIdAes128Cfb, FidAes192Ecb, FIdAes192Cbc,
-      FIdAes192Ofb, FIdAes192Cfb, FIdAes256Ecb, FIdAes256Cbc, FIdAes256Ofb,
-      FIdAes256Cfb, FIdDsaWithSha2, FDsaWithSha224, FDsaWithSha256,
-      FDsaWithSha384, FDsaWithSha512, FIdDsaWithSha3_224, FIdDsaWithSha3_256,
-      FIdDsaWithSha3_384, FIdDsaWithSha3_512, FIdECDsaWithSha3_224,
-      FIdECDsaWithSha3_256, FIdECDsaWithSha3_384, FIdECDsaWithSha3_512
-      : IDerObjectIdentifier;
+      FIdSha3_384, FIdSha3_512, FIdShake128, FIdShake256, FIdHMacWithSha3_224,
+      FIdHMacWithSha3_256, FIdHMacWithSha3_384, FIdHMacWithSha3_512, FAES,
+      FIdAES128Ecb, FIdAes128Cbc, FIdAes128Ofb, FIdAes128Cfb, FidAes192Ecb,
+      FIdAes192Cbc, FIdAes192Ofb, FIdAes192Cfb, FIdAes256Ecb, FIdAes256Cbc,
+      FIdAes256Ofb, FIdAes256Cfb, FIdDsaWithSha2, FDsaWithSha224,
+      FDsaWithSha256, FDsaWithSha384, FDsaWithSha512, FIdDsaWithSha3_224,
+      FIdDsaWithSha3_256, FIdDsaWithSha3_384, FIdDsaWithSha3_512,
+      FIdECDsaWithSha3_224, FIdECDsaWithSha3_256, FIdECDsaWithSha3_384,
+      FIdECDsaWithSha3_512: IDerObjectIdentifier;
 
     class function GetNistAlgorithm: IDerObjectIdentifier; static; inline;
     class function GetHashAlgs: IDerObjectIdentifier; static; inline;
@@ -55,6 +55,8 @@ type
     class function GetIdSha3_256: IDerObjectIdentifier; static; inline;
     class function GetIdSha3_384: IDerObjectIdentifier; static; inline;
     class function GetIdSha3_512: IDerObjectIdentifier; static; inline;
+    class function GetIdShake128: IDerObjectIdentifier; static; inline;
+    class function GetIdShake256: IDerObjectIdentifier; static; inline;
     class function GetIdSha384: IDerObjectIdentifier; static; inline;
     class function GetIdSha512: IDerObjectIdentifier; static; inline;
     class function GetIdSha512_224: IDerObjectIdentifier; static; inline;
@@ -121,6 +123,8 @@ type
     class property IdSha3_256: IDerObjectIdentifier read GetIdSha3_256;
     class property IdSha3_384: IDerObjectIdentifier read GetIdSha3_384;
     class property IdSha3_512: IDerObjectIdentifier read GetIdSha3_512;
+    class property IdShake128: IDerObjectIdentifier read GetIdShake128;
+    class property IdShake256: IDerObjectIdentifier read GetIdShake256;
 
     class property IdHMacWithSha3_224: IDerObjectIdentifier
       read GetIdHMacWithSha3_224;
@@ -332,6 +336,16 @@ begin
   result := FIdSha3_512;
 end;
 
+class function TNistObjectIdentifiers.GetIdShake128: IDerObjectIdentifier;
+begin
+  result := FIdShake128;
+end;
+
+class function TNistObjectIdentifiers.GetIdShake256: IDerObjectIdentifier;
+begin
+  result := FIdShake256;
+end;
+
 class function TNistObjectIdentifiers.GetIdSha512: IDerObjectIdentifier;
 begin
   result := FIdSha512;
@@ -427,7 +441,8 @@ begin
     FIdSha3_256 := HashAlgs.Branch('8');
     FIdSha3_384 := HashAlgs.Branch('9');
     FIdSha3_512 := HashAlgs.Branch('10');
-
+    FIdShake128 := HashAlgs.Branch('11');
+    FIdShake256 := HashAlgs.Branch('12');
     FIdHMacWithSha3_224 := HashAlgs.Branch('13');
     FIdHMacWithSha3_256 := HashAlgs.Branch('14');
     FIdHMacWithSha3_384 := HashAlgs.Branch('15');

+ 16 - 2
CryptoLib/src/Asn1/Pkcs/ClpPkcsObjectIdentifiers.pas

@@ -35,13 +35,20 @@ type
     // object identifiers for digests
     //
     DigestAlgorithm: String = '1.2.840.113549.2';
+    //
+    // pkcs-3 OBJECT IDENTIFIER ::= {
+    // iso(1) member-body(2) us(840) rsadsi(113549) pkcs(1) 3 }
+    //
+    Pkcs3: String = '1.2.840.113549.1.3';
 
   class var
 
     FIsBooted: Boolean;
-    FMD2, FMD4, FMD5, FIdHmacWithSha1, FIdHmacWithSha224, FIdHmacWithSha256,
-      FIdHmacWithSha384, FIdHmacWithSha512: IDerObjectIdentifier;
+    FDhKeyAgreement, FMD2, FMD4, FMD5, FIdHmacWithSha1, FIdHmacWithSha224,
+      FIdHmacWithSha256, FIdHmacWithSha384, FIdHmacWithSha512
+      : IDerObjectIdentifier;
 
+    class function GetDhKeyAgreement: IDerObjectIdentifier; static; inline;
     class function GetMD2: IDerObjectIdentifier; static; inline;
     class function GetMD4: IDerObjectIdentifier; static; inline;
     class function GetMD5: IDerObjectIdentifier; static; inline;
@@ -56,6 +63,7 @@ type
 
   public
 
+    class property DhKeyAgreement: IDerObjectIdentifier read GetDhKeyAgreement;
     //
     // md2 OBJECT IDENTIFIER ::=
     // {iso(1) member-body(2) US(840) rsadsi(113549) DigestAlgorithm(2) 2}
@@ -94,6 +102,7 @@ class procedure TPkcsObjectIdentifiers.Boot;
 begin
   if not FIsBooted then
   begin
+    FDhKeyAgreement := TDerObjectIdentifier.Create(Pkcs3 + '.1');
     FMD2 := TDerObjectIdentifier.Create(DigestAlgorithm + '.2');
     FMD4 := TDerObjectIdentifier.Create(DigestAlgorithm + '.4');
     FMD5 := TDerObjectIdentifier.Create(DigestAlgorithm + '.5');
@@ -107,6 +116,11 @@ begin
   end;
 end;
 
+class function TPkcsObjectIdentifiers.GetDhKeyAgreement: IDerObjectIdentifier;
+begin
+  result := FDhKeyAgreement;
+end;
+
 class function TPkcsObjectIdentifiers.GetIdHmacWithSha1: IDerObjectIdentifier;
 begin
   result := FIdHmacWithSha1;

+ 0 - 1
CryptoLib/src/Asn1/Sec/ClpSecNamedCurves.pas

@@ -802,7 +802,6 @@ begin
   begin
     result := GetByOid(oid);
   end;
-
 end;
 
 class function TSecNamedCurves.GetName(const oid: IDerObjectIdentifier): String;

+ 968 - 0
CryptoLib/src/Asn1/TeleTrust/ClpTeleTrusTNamedCurves.pas

@@ -0,0 +1,968 @@
+{ *********************************************************************************** }
+{ *                              CryptoLib Library                                  * }
+{ *                Copyright (c) 2018 - 20XX Ugochukwu Mmaduekwe                    * }
+{ *                 Github Repository <https://github.com/Xor-el>                   * }
+
+{ *  Distributed under the MIT software license, see the accompanying file LICENSE  * }
+{ *          or visit http://www.opensource.org/licenses/mit-license.php.           * }
+
+{ *                              Acknowledgements:                                  * }
+{ *                                                                                 * }
+{ *      Thanks to Sphere 10 Software (http://www.sphere10.com/) for sponsoring     * }
+{ *                           development of this library                           * }
+
+{ * ******************************************************************************* * }
+
+(* &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&& *)
+
+unit ClpTeleTrusTNamedCurves;
+
+{$I ..\..\Include\CryptoLib.inc}
+
+interface
+
+uses
+  SysUtils,
+  Generics.Collections,
+  ClpEncoders,
+  ClpTeleTrusTObjectIdentifiers,
+  ClpCryptoLibTypes,
+  ClpBigInteger,
+  ClpECC,
+  ClpIECC,
+  ClpX9ECC,
+  ClpIX9ECC,
+  ClpIAsn1Objects,
+  ClpX9ECParameters,
+  ClpIX9ECParameters,
+  ClpX9ECParametersHolder,
+  ClpIX9ECParametersHolder;
+
+type
+
+  /// <summary>
+  /// elliptic curves defined in 'ECC Brainpool Standard Curves and Curve
+  /// Generation' <br /><see href="http://www.ecc-brainpool.org/download/draft_pkix_additional_ecc_dp.txt" />
+  /// </summary>
+  TTeleTrusTNamedCurves = class sealed(TObject)
+
+  strict private
+
+  class var
+    FobjIds: TDictionary<String, IDerObjectIdentifier>;
+    Fnames: TDictionary<IDerObjectIdentifier, String>;
+    Fcurves: TDictionary<IDerObjectIdentifier, IX9ECParametersHolder>;
+
+    class function GetNames: TCryptoLibStringArray; static; inline;
+    class procedure DefineCurve(const name: String;
+      const oid: IDerObjectIdentifier; const holder: IX9ECParametersHolder);
+      static; inline;
+
+    class function ConfigureCurve(const curve: IECCurve): IECCurve;
+      static; inline;
+
+    class procedure Boot(); static;
+    class constructor CreateTeleTrusTNamedCurves();
+    class destructor DestroyTeleTrusTNamedCurves();
+
+  public
+    class function GetByName(const name: String): IX9ECParameters;
+      static; inline;
+    // /**
+    // * return the X9ECParameters object for the named curve represented by
+    // * the passed in object identifier. Null if the curve isn't present.
+    // *
+    // * @param oid an object identifier representing a named curve, if present.
+    // */
+    class function GetByOid(const oid: IDerObjectIdentifier): IX9ECParameters;
+      static; inline;
+    // /**
+    // * return the object identifier signified by the passed in name. Null
+    // * if there is no object identifier associated with name.
+    // *
+    // * @return the object identifier associated with name, if present.
+    // */
+    class function GetOid(const name: String): IDerObjectIdentifier;
+      static; inline;
+    // /**
+    // * return the named curve name represented by the given object identifier.
+    // */
+    class function GetName(const oid: IDerObjectIdentifier): String;
+      static; inline;
+    // /**
+    // * returns an enumeration containing the name strings for curves
+    // * contained in this structure.
+    // */
+    class property Names: TCryptoLibStringArray read GetNames;
+
+  type
+
+    /// <summary>
+    /// brainpoolP160r1
+    /// </summary>
+    TBrainpoolP160r1Holder = class sealed(TX9ECParametersHolder,
+      IX9ECParametersHolder)
+
+    strict protected
+      function CreateParameters(): IX9ECParameters; override;
+
+    public
+      class function Instance(): IX9ECParametersHolder; static;
+
+    end;
+
+  type
+
+    /// <summary>
+    /// brainpoolP160t1
+    /// </summary>
+    TBrainpoolP160t1Holder = class sealed(TX9ECParametersHolder,
+      IX9ECParametersHolder)
+
+    strict protected
+      function CreateParameters(): IX9ECParameters; override;
+
+    public
+      class function Instance(): IX9ECParametersHolder; static;
+
+    end;
+
+  type
+
+    /// <summary>
+    /// brainpoolP192r1
+    /// </summary>
+    TBrainpoolP192r1Holder = class sealed(TX9ECParametersHolder,
+      IX9ECParametersHolder)
+
+    strict protected
+      function CreateParameters(): IX9ECParameters; override;
+
+    public
+      class function Instance(): IX9ECParametersHolder; static;
+
+    end;
+
+  type
+
+    /// <summary>
+    /// brainpoolP192t1
+    /// </summary>
+    TBrainpoolP192t1Holder = class sealed(TX9ECParametersHolder,
+      IX9ECParametersHolder)
+
+    strict protected
+      function CreateParameters(): IX9ECParameters; override;
+
+    public
+      class function Instance(): IX9ECParametersHolder; static;
+
+    end;
+
+  type
+
+    /// <summary>
+    /// brainpoolP224r1
+    /// </summary>
+    TBrainpoolP224r1Holder = class sealed(TX9ECParametersHolder,
+      IX9ECParametersHolder)
+
+    strict protected
+      function CreateParameters(): IX9ECParameters; override;
+
+    public
+      class function Instance(): IX9ECParametersHolder; static;
+
+    end;
+
+  type
+
+    /// <summary>
+    /// brainpoolP224t1
+    /// </summary>
+    TBrainpoolP224t1Holder = class sealed(TX9ECParametersHolder,
+      IX9ECParametersHolder)
+
+    strict protected
+      function CreateParameters(): IX9ECParameters; override;
+
+    public
+      class function Instance(): IX9ECParametersHolder; static;
+
+    end;
+
+  type
+
+    /// <summary>
+    /// brainpoolP256r1
+    /// </summary>
+    TBrainpoolP256r1Holder = class sealed(TX9ECParametersHolder,
+      IX9ECParametersHolder)
+
+    strict protected
+      function CreateParameters(): IX9ECParameters; override;
+
+    public
+      class function Instance(): IX9ECParametersHolder; static;
+
+    end;
+
+  type
+
+    /// <summary>
+    /// brainpoolP256t1
+    /// </summary>
+    TBrainpoolP256t1Holder = class sealed(TX9ECParametersHolder,
+      IX9ECParametersHolder)
+
+    strict protected
+      function CreateParameters(): IX9ECParameters; override;
+
+    public
+      class function Instance(): IX9ECParametersHolder; static;
+
+    end;
+
+  type
+
+    /// <summary>
+    /// brainpoolP320r1
+    /// </summary>
+    TBrainpoolP320r1Holder = class sealed(TX9ECParametersHolder,
+      IX9ECParametersHolder)
+
+    strict protected
+      function CreateParameters(): IX9ECParameters; override;
+
+    public
+      class function Instance(): IX9ECParametersHolder; static;
+
+    end;
+
+  type
+
+    /// <summary>
+    /// brainpoolP320t1
+    /// </summary>
+    TBrainpoolP320t1Holder = class sealed(TX9ECParametersHolder,
+      IX9ECParametersHolder)
+
+    strict protected
+      function CreateParameters(): IX9ECParameters; override;
+
+    public
+      class function Instance(): IX9ECParametersHolder; static;
+
+    end;
+
+  type
+
+    /// <summary>
+    /// brainpoolP384r1
+    /// </summary>
+    TBrainpoolP384r1Holder = class sealed(TX9ECParametersHolder,
+      IX9ECParametersHolder)
+
+    strict protected
+      function CreateParameters(): IX9ECParameters; override;
+
+    public
+      class function Instance(): IX9ECParametersHolder; static;
+
+    end;
+
+  type
+
+    /// <summary>
+    /// brainpoolP384t1
+    /// </summary>
+    TBrainpoolP384t1Holder = class sealed(TX9ECParametersHolder,
+      IX9ECParametersHolder)
+
+    strict protected
+      function CreateParameters(): IX9ECParameters; override;
+
+    public
+      class function Instance(): IX9ECParametersHolder; static;
+
+    end;
+
+  type
+
+    /// <summary>
+    /// brainpoolP512r1
+    /// </summary>
+    TBrainpoolP512r1Holder = class sealed(TX9ECParametersHolder,
+      IX9ECParametersHolder)
+
+    strict protected
+      function CreateParameters(): IX9ECParameters; override;
+
+    public
+      class function Instance(): IX9ECParametersHolder; static;
+
+    end;
+
+  type
+
+    /// <summary>
+    /// brainpoolP512t1
+    /// </summary>
+    TBrainpoolP512t1Holder = class sealed(TX9ECParametersHolder,
+      IX9ECParametersHolder)
+
+    strict protected
+      function CreateParameters(): IX9ECParameters; override;
+
+    public
+      class function Instance(): IX9ECParametersHolder; static;
+
+    end;
+
+  end;
+
+implementation
+
+{ TeleTrusTNamedCurves }
+
+class function TTeleTrusTNamedCurves.ConfigureCurve(const curve: IECCurve)
+  : IECCurve;
+begin
+  result := curve;
+end;
+
+class constructor TTeleTrusTNamedCurves.CreateTeleTrusTNamedCurves;
+begin
+  TTeleTrusTNamedCurves.Boot;
+end;
+
+class destructor TTeleTrusTNamedCurves.DestroyTeleTrusTNamedCurves;
+begin
+  FobjIds.Free;
+  Fnames.Free;
+  Fcurves.Free;
+end;
+
+class procedure TTeleTrusTNamedCurves.DefineCurve(const name: String;
+  const oid: IDerObjectIdentifier; const holder: IX9ECParametersHolder);
+begin
+  FobjIds.Add(UpperCase(name), oid);
+  Fnames.Add(oid, name);
+  Fcurves.Add(oid, holder);
+end;
+
+class function TTeleTrusTNamedCurves.GetByOid(const oid: IDerObjectIdentifier)
+  : IX9ECParameters;
+var
+  holder: IX9ECParametersHolder;
+begin
+  if Fcurves.TryGetValue(oid, holder) then
+  begin
+    result := holder.Parameters
+  end
+  else
+  begin
+    result := Nil;
+  end;
+end;
+
+class function TTeleTrusTNamedCurves.GetOid(const name: String)
+  : IDerObjectIdentifier;
+begin
+  if not(FobjIds.TryGetValue(UpperCase(name), result)) then
+  begin
+    result := Nil;
+  end;
+end;
+
+class function TTeleTrusTNamedCurves.GetByName(const name: String)
+  : IX9ECParameters;
+var
+  oid: IDerObjectIdentifier;
+begin
+  oid := GetOid(name);
+  if oid = Nil then
+  begin
+    result := Nil;
+  end
+  else
+  begin
+    result := GetByOid(oid);
+  end;
+end;
+
+class function TTeleTrusTNamedCurves.GetName
+  (const oid: IDerObjectIdentifier): String;
+begin
+  if not(Fnames.TryGetValue(oid, result)) then
+  begin
+    result := '';
+  end;
+end;
+
+class function TTeleTrusTNamedCurves.GetNames: TCryptoLibStringArray;
+begin
+  result := Fnames.Values.ToArray();
+end;
+
+class procedure TTeleTrusTNamedCurves.Boot;
+begin
+  FobjIds := TDictionary<String, IDerObjectIdentifier>.Create();
+  Fnames := TDictionary<IDerObjectIdentifier, String>.Create();
+  Fcurves := TDictionary<IDerObjectIdentifier, IX9ECParametersHolder>.Create();
+
+  DefineCurve('brainpoolP160r1', TTeleTrusTObjectIdentifiers.BrainpoolP160R1,
+    TBrainpoolP160r1Holder.Instance);
+  DefineCurve('brainpoolP160t1', TTeleTrusTObjectIdentifiers.BrainpoolP160T1,
+    TBrainpoolP160t1Holder.Instance);
+  DefineCurve('brainpoolP192r1', TTeleTrusTObjectIdentifiers.BrainpoolP192R1,
+    TBrainpoolP160t1Holder.Instance);
+  DefineCurve('brainpoolP192t1', TTeleTrusTObjectIdentifiers.BrainpoolP192T1,
+    TBrainpoolP192t1Holder.Instance);
+  DefineCurve('brainpoolP224r1', TTeleTrusTObjectIdentifiers.BrainpoolP224R1,
+    TBrainpoolP224r1Holder.Instance);
+  DefineCurve('brainpoolP224t1', TTeleTrusTObjectIdentifiers.BrainpoolP224T1,
+    TBrainpoolP224t1Holder.Instance);
+  DefineCurve('brainpoolP256r1', TTeleTrusTObjectIdentifiers.BrainpoolP256R1,
+    TBrainpoolP256r1Holder.Instance);
+  DefineCurve('brainpoolP256t1', TTeleTrusTObjectIdentifiers.BrainpoolP256T1,
+    TBrainpoolP256t1Holder.Instance);
+  DefineCurve('brainpoolP320r1', TTeleTrusTObjectIdentifiers.BrainpoolP320R1,
+    TBrainpoolP320r1Holder.Instance);
+  DefineCurve('brainpoolP320t1', TTeleTrusTObjectIdentifiers.BrainpoolP320T1,
+    TBrainpoolP320t1Holder.Instance);
+  DefineCurve('brainpoolP384r1', TTeleTrusTObjectIdentifiers.BrainpoolP384R1,
+    TBrainpoolP384r1Holder.Instance);
+  DefineCurve('brainpoolP384t1', TTeleTrusTObjectIdentifiers.BrainpoolP384T1,
+    TBrainpoolP384t1Holder.Instance);
+  DefineCurve('brainpoolP512r1', TTeleTrusTObjectIdentifiers.BrainpoolP512R1,
+    TBrainpoolP512r1Holder.Instance);
+  DefineCurve('brainpoolP512t1', TTeleTrusTObjectIdentifiers.BrainpoolP512T1,
+    TBrainpoolP512t1Holder.Instance);
+end;
+
+{ TeleTrusTNamedCurves.TBrainpoolP160r1Holder }
+
+function TTeleTrusTNamedCurves.TBrainpoolP160r1Holder.CreateParameters
+  : IX9ECParameters;
+var
+  n, h: TBigInteger;
+  curve: IECCurve;
+begin
+  n := TBigInteger.Create('E95E4A5F737059DC60DF5991D45029409E60FC09', 16);
+  h := TBigInteger.Create('01', 16);
+
+  curve := ConfigureCurve
+    (TFpCurve.Create(TBigInteger.Create
+    ('E95E4A5F737059DC60DFC7AD95B3D8139515620F', 16), // q
+    TBigInteger.Create('340E7BE2A280EB74E2BE61BADA745D97E8F7C300', 16), // a
+    TBigInteger.Create('1E589A8595423412134FAA2DBDEC95C8D8675E58', 16), // b
+    n, h) as IFpCurve);
+
+  result := TX9ECParameters.Create(curve, TX9ECPoint.Create(curve,
+    THex.Decode
+    ('04BED5AF16EA3F6A4F62938C4631EB5AF7BDBCDBC31667CB477A1A8EC338F94741669C976316DA6321')
+    ) as IX9ECPoint, // G
+    n, h);
+end;
+
+class function TTeleTrusTNamedCurves.TBrainpoolP160r1Holder.Instance
+  : IX9ECParametersHolder;
+begin
+  result := TBrainpoolP160r1Holder.Create();
+end;
+
+{ TeleTrusTNamedCurves.TBrainpoolP160t1Holder }
+
+function TTeleTrusTNamedCurves.TBrainpoolP160t1Holder.CreateParameters
+  : IX9ECParameters;
+var
+  n, h: TBigInteger;
+  curve: IECCurve;
+begin
+  n := TBigInteger.Create('E95E4A5F737059DC60DF5991D45029409E60FC09', 16);
+  h := TBigInteger.Create('01', 16);
+
+  curve := ConfigureCurve
+    (TFpCurve.Create(TBigInteger.Create
+    ('E95E4A5F737059DC60DFC7AD95B3D8139515620F', 16), // q
+    TBigInteger.Create('E95E4A5F737059DC60DFC7AD95B3D8139515620C', 16), // a'
+    TBigInteger.Create('7A556B6DAE535B7B51ED2C4D7DAA7A0B5C55F380', 16), // b'
+    n, h) as IFpCurve);
+
+  result := TX9ECParameters.Create(curve, TX9ECPoint.Create(curve,
+    THex.Decode
+    ('04B199B13B9B34EFC1397E64BAEB05ACC265FF2378ADD6718B7C7C1961F0991B842443772152C9E0AD')
+    ) as IX9ECPoint, // G'
+    n, h);
+end;
+
+class function TTeleTrusTNamedCurves.TBrainpoolP160t1Holder.Instance
+  : IX9ECParametersHolder;
+begin
+  result := TBrainpoolP160t1Holder.Create();
+end;
+
+{ TeleTrusTNamedCurves.TBrainpoolP192r1Holder }
+
+function TTeleTrusTNamedCurves.TBrainpoolP192r1Holder.CreateParameters
+  : IX9ECParameters;
+var
+  n, h: TBigInteger;
+  curve: IECCurve;
+begin
+  n := TBigInteger.Create
+    ('C302F41D932A36CDA7A3462F9E9E916B5BE8F1029AC4ACC1', 16);
+  h := TBigInteger.Create('01', 16);
+
+  curve := ConfigureCurve
+    (TFpCurve.Create(TBigInteger.Create
+    ('C302F41D932A36CDA7A3463093D18DB78FCE476DE1A86297', 16), // q
+    TBigInteger.Create('6A91174076B1E0E19C39C031FE8685C1CAE040E5C69A28EF', 16),
+    // a
+    TBigInteger.Create('469A28EF7C28CCA3DC721D044F4496BCCA7EF4146FBF25C9', 16),
+    // b
+    n, h) as IFpCurve);
+
+  result := TX9ECParameters.Create(curve, TX9ECPoint.Create(curve,
+    THex.Decode
+    ('04C0A0647EAAB6A48753B033C56CB0F0900A2F5C4853375FD614B690866ABD5BB88B5F4828C1490002E6773FA2FA299B8F')
+    ) as IX9ECPoint, // G
+    n, h);
+end;
+
+class function TTeleTrusTNamedCurves.TBrainpoolP192r1Holder.Instance
+  : IX9ECParametersHolder;
+begin
+  result := TBrainpoolP192r1Holder.Create();
+end;
+
+{ TeleTrusTNamedCurves.TBrainpoolP192t1Holder }
+
+function TTeleTrusTNamedCurves.TBrainpoolP192t1Holder.CreateParameters
+  : IX9ECParameters;
+var
+  n, h: TBigInteger;
+  curve: IECCurve;
+begin
+  n := TBigInteger.Create
+    ('C302F41D932A36CDA7A3462F9E9E916B5BE8F1029AC4ACC1', 16);
+  h := TBigInteger.Create('01', 16);
+
+  curve := ConfigureCurve
+    (TFpCurve.Create(TBigInteger.Create
+    ('C302F41D932A36CDA7A3463093D18DB78FCE476DE1A86297', 16), // q
+    TBigInteger.Create('C302F41D932A36CDA7A3463093D18DB78FCE476DE1A86294', 16),
+    // a'
+    TBigInteger.Create('13D56FFAEC78681E68F9DEB43B35BEC2FB68542E27897B79', 16),
+    // b'
+    n, h) as IFpCurve);
+
+  result := TX9ECParameters.Create(curve, TX9ECPoint.Create(curve,
+    THex.Decode
+    ('043AE9E58C82F63C30282E1FE7BBF43FA72C446AF6F4618129097E2C5667C2223A902AB5CA449D0084B7E5B3DE7CCC01C9')
+    ) as IX9ECPoint, // G'
+    n, h);
+end;
+
+class function TTeleTrusTNamedCurves.TBrainpoolP192t1Holder.Instance
+  : IX9ECParametersHolder;
+begin
+  result := TBrainpoolP192t1Holder.Create();
+end;
+
+{ TeleTrusTNamedCurves.TBrainpoolP224r1Holder }
+
+function TTeleTrusTNamedCurves.TBrainpoolP224r1Holder.CreateParameters
+  : IX9ECParameters;
+var
+  n, h: TBigInteger;
+  curve: IECCurve;
+begin
+  n := TBigInteger.Create
+    ('D7C134AA264366862A18302575D0FB98D116BC4B6DDEBCA3A5A7939F', 16);
+  h := TBigInteger.Create('01', 16);
+
+  curve := ConfigureCurve
+    (TFpCurve.Create(TBigInteger.Create
+    ('D7C134AA264366862A18302575D1D787B09F075797DA89F57EC8C0FF', 16), // q
+    TBigInteger.Create
+    ('68A5E62CA9CE6C1C299803A6C1530B514E182AD8B0042A59CAD29F43', 16),
+    // a
+    TBigInteger.Create
+    ('2580F63CCFE44138870713B1A92369E33E2135D266DBB372386C400B', 16),
+    // b
+    n, h) as IFpCurve);
+
+  result := TX9ECParameters.Create(curve, TX9ECPoint.Create(curve,
+    THex.Decode
+    ('040D9029AD2C7E5CF4340823B2A87DC68C9E4CE3174C1E6EFDEE12C07D58AA56F772C0726F24C6B89E4ECDAC24354B9E99CAA3F6D3761402CD')
+    ) as IX9ECPoint, // G
+    n, h);
+end;
+
+class function TTeleTrusTNamedCurves.TBrainpoolP224r1Holder.Instance
+  : IX9ECParametersHolder;
+begin
+  result := TBrainpoolP224r1Holder.Create();
+end;
+
+{ TeleTrusTNamedCurves.TBrainpoolP224t1Holder }
+
+function TTeleTrusTNamedCurves.TBrainpoolP224t1Holder.CreateParameters
+  : IX9ECParameters;
+var
+  n, h: TBigInteger;
+  curve: IECCurve;
+begin
+  n := TBigInteger.Create
+    ('D7C134AA264366862A18302575D0FB98D116BC4B6DDEBCA3A5A7939F', 16);
+  h := TBigInteger.Create('01', 16);
+
+  curve := ConfigureCurve
+    (TFpCurve.Create(TBigInteger.Create
+    ('D7C134AA264366862A18302575D1D787B09F075797DA89F57EC8C0FF', 16), // q
+    TBigInteger.Create
+    ('D7C134AA264366862A18302575D1D787B09F075797DA89F57EC8C0FC', 16),
+    // a'
+    TBigInteger.Create
+    ('4B337D934104CD7BEF271BF60CED1ED20DA14C08B3BB64F18A60888D', 16),
+    // b'
+    n, h) as IFpCurve);
+
+  result := TX9ECParameters.Create(curve, TX9ECPoint.Create(curve,
+    THex.Decode
+    ('046AB1E344CE25FF3896424E7FFE14762ECB49F8928AC0C76029B4D5800374E9F5143E568CD23F3F4D7C0D4B1E41C8CC0D1C6ABD5F1A46DB4C')
+    ) as IX9ECPoint, // G'
+    n, h);
+end;
+
+class function TTeleTrusTNamedCurves.TBrainpoolP224t1Holder.Instance
+  : IX9ECParametersHolder;
+begin
+  result := TBrainpoolP224t1Holder.Create();
+end;
+
+{ TeleTrusTNamedCurves.TBrainpoolP256r1Holder }
+
+function TTeleTrusTNamedCurves.TBrainpoolP256r1Holder.CreateParameters
+  : IX9ECParameters;
+var
+  n, h: TBigInteger;
+  curve: IECCurve;
+begin
+  n := TBigInteger.Create
+    ('A9FB57DBA1EEA9BC3E660A909D838D718C397AA3B561A6F7901E0E82974856A7', 16);
+  h := TBigInteger.Create('01', 16);
+
+  curve := ConfigureCurve
+    (TFpCurve.Create(TBigInteger.Create
+    ('A9FB57DBA1EEA9BC3E660A909D838D726E3BF623D52620282013481D1F6E5377', 16),
+    // q
+    TBigInteger.Create
+    ('7D5A0975FC2C3057EEF67530417AFFE7FB8055C126DC5C6CE94A4B44F330B5D9', 16),
+    // a
+    TBigInteger.Create
+    ('26DC5C6CE94A4B44F330B5D9BBD77CBF958416295CF7E1CE6BCCDC18FF8C07B6', 16),
+    // b
+    n, h) as IFpCurve);
+
+  result := TX9ECParameters.Create(curve, TX9ECPoint.Create(curve,
+    THex.Decode
+    ('048BD2AEB9CB7E57CB2C4B482FFC81B7AFB9DE27E1E3BD23C23A4453BD9ACE3262547EF835C3DAC4FD97F8461A14611DC9C27745132DED8E545C1D54C72F046997')
+    ) as IX9ECPoint, // G
+    n, h);
+end;
+
+class function TTeleTrusTNamedCurves.TBrainpoolP256r1Holder.Instance
+  : IX9ECParametersHolder;
+begin
+  result := TBrainpoolP256r1Holder.Create();
+end;
+
+{ TeleTrusTNamedCurves.TBrainpoolP256t1Holder }
+
+function TTeleTrusTNamedCurves.TBrainpoolP256t1Holder.CreateParameters
+  : IX9ECParameters;
+var
+  n, h: TBigInteger;
+  curve: IECCurve;
+begin
+  n := TBigInteger.Create
+    ('A9FB57DBA1EEA9BC3E660A909D838D718C397AA3B561A6F7901E0E82974856A7', 16);
+  h := TBigInteger.Create('01', 16);
+
+  curve := ConfigureCurve
+    (TFpCurve.Create(TBigInteger.Create
+    ('A9FB57DBA1EEA9BC3E660A909D838D726E3BF623D52620282013481D1F6E5377', 16),
+    // q
+    TBigInteger.Create
+    ('A9FB57DBA1EEA9BC3E660A909D838D726E3BF623D52620282013481D1F6E5374', 16),
+    // a'
+    TBigInteger.Create
+    ('662C61C430D84EA4FE66A7733D0B76B7BF93EBC4AF2F49256AE58101FEE92B04', 16),
+    // b'
+    n, h) as IFpCurve);
+
+  result := TX9ECParameters.Create(curve, TX9ECPoint.Create(curve,
+    THex.Decode
+    ('04A3E8EB3CC1CFE7B7732213B23A656149AFA142C47AAFBC2B79A191562E1305F42D996C823439C56D7F7B22E14644417E69BCB6DE39D027001DABE8F35B25C9BE')
+    ) as IX9ECPoint, // G'
+    n, h);
+end;
+
+class function TTeleTrusTNamedCurves.TBrainpoolP256t1Holder.Instance
+  : IX9ECParametersHolder;
+begin
+  result := TBrainpoolP256t1Holder.Create();
+end;
+
+{ TeleTrusTNamedCurves.TBrainpoolP320r1Holder }
+
+function TTeleTrusTNamedCurves.TBrainpoolP320r1Holder.CreateParameters
+  : IX9ECParameters;
+var
+  n, h: TBigInteger;
+  curve: IECCurve;
+begin
+  n := TBigInteger.Create
+    ('D35E472036BC4FB7E13C785ED201E065F98FCFA5B68F12A32D482EC7EE8658E98691555B44C59311',
+    16);
+  h := TBigInteger.Create('01', 16);
+
+  curve := ConfigureCurve
+    (TFpCurve.Create(TBigInteger.Create
+    ('D35E472036BC4FB7E13C785ED201E065F98FCFA6F6F40DEF4F92B9EC7893EC28FCD412B1F1B32E27',
+    16),
+    // q
+    TBigInteger.Create
+    ('3EE30B568FBAB0F883CCEBD46D3F3BB8A2A73513F5EB79DA66190EB085FFA9F492F375A97D860EB4',
+    16),
+    // a
+    TBigInteger.Create
+    ('520883949DFDBC42D3AD198640688A6FE13F41349554B49ACC31DCCD884539816F5EB4AC8FB1F1A6',
+    16),
+    // b
+    n, h) as IFpCurve);
+
+  result := TX9ECParameters.Create(curve, TX9ECPoint.Create(curve,
+    THex.Decode
+    ('0443BD7E9AFB53D8B85289BCC48EE5BFE6F20137D10A087EB6E7871E2A10A599C710AF8D0D39E2061114FDD05545EC1CC8AB4093247F77275E0743FFED117182EAA9C77877AAAC6AC7D35245D1692E8EE1')
+    ) as IX9ECPoint, // G
+    n, h);
+end;
+
+class function TTeleTrusTNamedCurves.TBrainpoolP320r1Holder.Instance
+  : IX9ECParametersHolder;
+begin
+  result := TBrainpoolP320r1Holder.Create();
+end;
+
+{ TeleTrusTNamedCurves.TBrainpoolP320t1Holder }
+
+function TTeleTrusTNamedCurves.TBrainpoolP320t1Holder.CreateParameters
+  : IX9ECParameters;
+var
+  n, h: TBigInteger;
+  curve: IECCurve;
+begin
+  n := TBigInteger.Create
+    ('D35E472036BC4FB7E13C785ED201E065F98FCFA5B68F12A32D482EC7EE8658E98691555B44C59311',
+    16);
+  h := TBigInteger.Create('01', 16);
+
+  curve := ConfigureCurve
+    (TFpCurve.Create(TBigInteger.Create
+    ('D35E472036BC4FB7E13C785ED201E065F98FCFA6F6F40DEF4F92B9EC7893EC28FCD412B1F1B32E27',
+    16),
+    // q
+    TBigInteger.Create
+    ('D35E472036BC4FB7E13C785ED201E065F98FCFA6F6F40DEF4F92B9EC7893EC28FCD412B1F1B32E24',
+    16),
+    // a'
+    TBigInteger.Create
+    ('A7F561E038EB1ED560B3D147DB782013064C19F27ED27C6780AAF77FB8A547CEB5B4FEF422340353',
+    16),
+    // b'
+    n, h) as IFpCurve);
+
+  result := TX9ECParameters.Create(curve, TX9ECPoint.Create(curve,
+    THex.Decode
+    ('04925BE9FB01AFC6FB4D3E7D4990010F813408AB106C4F09CB7EE07868CC136FFF3357F624A21BED5263BA3A7A27483EBF6671DBEF7ABB30EBEE084E58A0B077AD42A5A0989D1EE71B1B9BC0455FB0D2C3')
+    ) as IX9ECPoint, // G'
+    n, h);
+end;
+
+class function TTeleTrusTNamedCurves.TBrainpoolP320t1Holder.Instance
+  : IX9ECParametersHolder;
+begin
+  result := TBrainpoolP320t1Holder.Create();
+end;
+
+{ TeleTrusTNamedCurves.TBrainpoolP384r1Holder }
+
+function TTeleTrusTNamedCurves.TBrainpoolP384r1Holder.CreateParameters
+  : IX9ECParameters;
+var
+  n, h: TBigInteger;
+  curve: IECCurve;
+begin
+  n := TBigInteger.Create
+    ('8CB91E82A3386D280F5D6F7E50E641DF152F7109ED5456B31F166E6CAC0425A7CF3AB6AF6B7FC3103B883202E9046565',
+    16);
+  h := TBigInteger.Create('01', 16);
+
+  curve := ConfigureCurve
+    (TFpCurve.Create(TBigInteger.Create
+    ('8CB91E82A3386D280F5D6F7E50E641DF152F7109ED5456B412B1DA197FB71123ACD3A729901D1A71874700133107EC53',
+    16),
+    // q
+    TBigInteger.Create
+    ('7BC382C63D8C150C3C72080ACE05AFA0C2BEA28E4FB22787139165EFBA91F90F8AA5814A503AD4EB04A8C7DD22CE2826',
+    16),
+    // a
+    TBigInteger.Create
+    ('4A8C7DD22CE28268B39B55416F0447C2FB77DE107DCD2A62E880EA53EEB62D57CB4390295DBC9943AB78696FA504C11',
+    16),
+    // b
+    n, h) as IFpCurve);
+
+  result := TX9ECParameters.Create(curve, TX9ECPoint.Create(curve,
+    THex.Decode
+    ('041D1C64F068CF45FFA2A63A81B7C13F6B8847A3E77EF14FE3DB7FCAFE0CBD10E8E826E03436D646AAEF87B2E247D4AF1E8ABE1D7520F9C2A45CB1EB8E95CFD55262B70B29FEEC5864E19C054FF99129280E4646217791811142820341263C5315')
+    ) as IX9ECPoint, // G
+    n, h);
+end;
+
+class function TTeleTrusTNamedCurves.TBrainpoolP384r1Holder.Instance
+  : IX9ECParametersHolder;
+begin
+  result := TBrainpoolP384r1Holder.Create();
+end;
+
+{ TeleTrusTNamedCurves.TBrainpoolP384t1Holder }
+
+function TTeleTrusTNamedCurves.TBrainpoolP384t1Holder.CreateParameters
+  : IX9ECParameters;
+var
+  n, h: TBigInteger;
+  curve: IECCurve;
+begin
+  n := TBigInteger.Create
+    ('8CB91E82A3386D280F5D6F7E50E641DF152F7109ED5456B31F166E6CAC0425A7CF3AB6AF6B7FC3103B883202E9046565',
+    16);
+  h := TBigInteger.Create('01', 16);
+
+  curve := ConfigureCurve
+    (TFpCurve.Create(TBigInteger.Create
+    ('8CB91E82A3386D280F5D6F7E50E641DF152F7109ED5456B412B1DA197FB71123ACD3A729901D1A71874700133107EC53',
+    16),
+    // q
+    TBigInteger.Create
+    ('8CB91E82A3386D280F5D6F7E50E641DF152F7109ED5456B412B1DA197FB71123ACD3A729901D1A71874700133107EC50',
+    16),
+    // a'
+    TBigInteger.Create
+    ('7F519EADA7BDA81BD826DBA647910F8C4B9346ED8CCDC64E4B1ABD11756DCE1D2074AA263B88805CED70355A33B471EE',
+    16),
+    // b'
+    n, h) as IFpCurve);
+
+  result := TX9ECParameters.Create(curve, TX9ECPoint.Create(curve,
+    THex.Decode
+    ('0418DE98B02DB9A306F2AFCD7235F72A819B80AB12EBD653172476FECD462AABFFC4FF191B946A5F54D8D0AA2F418808CC25AB056962D30651A114AFD2755AD336747F93475B7A1FCA3B88F2B6A208CCFE469408584DC2B2912675BF5B9E582928')
+    ) as IX9ECPoint, // G'
+    n, h);
+end;
+
+class function TTeleTrusTNamedCurves.TBrainpoolP384t1Holder.Instance
+  : IX9ECParametersHolder;
+begin
+  result := TBrainpoolP384t1Holder.Create();
+end;
+
+{ TeleTrusTNamedCurves.TBrainpoolP512r1Holder }
+
+function TTeleTrusTNamedCurves.TBrainpoolP512r1Holder.CreateParameters
+  : IX9ECParameters;
+var
+  n, h: TBigInteger;
+  curve: IECCurve;
+begin
+  n := TBigInteger.Create
+    ('AADD9DB8DBE9C48B3FD4E6AE33C9FC07CB308DB3B3C9D20ED6639CCA70330870553E5C414CA92619418661197FAC10471DB1D381085DDADDB58796829CA90069',
+    16);
+  h := TBigInteger.Create('01', 16);
+
+  curve := ConfigureCurve
+    (TFpCurve.Create(TBigInteger.Create
+    ('AADD9DB8DBE9C48B3FD4E6AE33C9FC07CB308DB3B3C9D20ED6639CCA703308717D4D9B009BC66842AECDA12AE6A380E62881FF2F2D82C68528AA6056583A48F3',
+    16),
+    // q
+    TBigInteger.Create
+    ('7830A3318B603B89E2327145AC234CC594CBDD8D3DF91610A83441CAEA9863BC2DED5D5AA8253AA10A2EF1C98B9AC8B57F1117A72BF2C7B9E7C1AC4D77FC94CA',
+    16),
+    // a
+    TBigInteger.Create
+    ('3DF91610A83441CAEA9863BC2DED5D5AA8253AA10A2EF1C98B9AC8B57F1117A72BF2C7B9E7C1AC4D77FC94CADC083E67984050B75EBAE5DD2809BD638016F723',
+    16),
+    // b
+    n, h) as IFpCurve);
+
+  result := TX9ECParameters.Create(curve, TX9ECPoint.Create(curve,
+    THex.Decode
+    ('0481AEE4BDD82ED9645A21322E9C4C6A9385ED9F70B5D916C1B43B62EEF4D0098EFF3B1F78E2D0D48D50D1687B93B97'
+    + 'D5F7C6D5047406A5E688B352209BCB9F8227DDE385D566332ECC0EABFA9CF7822FDF209F70024A57B1AA000C55B881F8111B2DCDE494A5F485E5BCA4BD88A2763AED1CA2B2FA8F0540678CD1E0F3AD80892')
+    ) as IX9ECPoint, // G
+    n, h);
+end;
+
+class function TTeleTrusTNamedCurves.TBrainpoolP512r1Holder.Instance
+  : IX9ECParametersHolder;
+begin
+  result := TBrainpoolP512r1Holder.Create();
+end;
+
+{ TeleTrusTNamedCurves.TBrainpoolP512t1Holder }
+
+function TTeleTrusTNamedCurves.TBrainpoolP512t1Holder.CreateParameters
+  : IX9ECParameters;
+var
+  n, h: TBigInteger;
+  curve: IECCurve;
+begin
+  n := TBigInteger.Create
+    ('AADD9DB8DBE9C48B3FD4E6AE33C9FC07CB308DB3B3C9D20ED6639CCA70330870553E5C414CA92619418661197FAC10471DB1D381085DDADDB58796829CA90069',
+    16);
+  h := TBigInteger.Create('01', 16);
+
+  curve := ConfigureCurve
+    (TFpCurve.Create(TBigInteger.Create
+    ('AADD9DB8DBE9C48B3FD4E6AE33C9FC07CB308DB3B3C9D20ED6639CCA703308717D4D9B009BC66842AECDA12AE6A380E62881FF2F2D82C68528AA6056583A48F3',
+    16),
+    // q
+    TBigInteger.Create
+    ('AADD9DB8DBE9C48B3FD4E6AE33C9FC07CB308DB3B3C9D20ED6639CCA703308717D4D9B009BC66842AECDA12AE6A380E62881FF2F2D82C68528AA6056583A48F0',
+    16),
+    // a'
+    TBigInteger.Create
+    ('7CBBBCF9441CFAB76E1890E46884EAE321F70C0BCB4981527897504BEC3E36A62BCDFA2304976540F6450085F2DAE145C22553B465763689180EA2571867423E',
+    16),
+    // b'
+    n, h) as IFpCurve);
+
+  result := TX9ECParameters.Create(curve, TX9ECPoint.Create(curve,
+    THex.Decode
+    ('04640ECE5C12788717B9C1BA06CBC2A6FEBA85842458C56DDE9DB1758D39C0313D82BA51735CDB3EA499AA77A7D'
+    + '6943A64F7A3F25FE26F06B51BAA2696FA9035DA5B534BD595F5AF0FA2C892376C84ACE1BB4E3019B71634C01131159CAE03CEE9D9932184BEEF216BD71DF2DADF86A627306ECFF96DBB8BACE198B61E00F8B332')
+    ) as IX9ECPoint, // G'
+    n, h);
+end;
+
+class function TTeleTrusTNamedCurves.TBrainpoolP512t1Holder.Instance
+  : IX9ECParametersHolder;
+begin
+  result := TBrainpoolP512t1Holder.Create();
+end;
+
+end.

+ 177 - 1
CryptoLib/src/Asn1/TeleTrust/ClpTeleTrusTObjectIdentifiers.pas

@@ -34,7 +34,12 @@ type
 
     FIsBooted: Boolean;
     FTeleTrusTAlgorithm, FRipeMD160, FRipeMD128, FRipeMD256, FECSign,
-      FECSignWithSha1, FECSignWithRipeMD160: IDerObjectIdentifier;
+      FECSignWithSha1, FECSignWithRipeMD160, FEccBrainpool, FEllipticCurve,
+      FVersionOne, FBrainpoolP160R1, FBrainpoolP160T1, FBrainpoolP192R1,
+      FBrainpoolP192T1, FBrainpoolP224R1, FBrainpoolP224T1, FBrainpoolP256R1,
+      FBrainpoolP256T1, FBrainpoolP320R1, FBrainpoolP320T1, FBrainpoolP384R1,
+      FBrainpoolP384T1, FBrainpoolP512R1, FBrainpoolP512T1
+      : IDerObjectIdentifier;
 
     class function GetRipeMD128: IDerObjectIdentifier; static; inline;
     class function GetRipeMD160: IDerObjectIdentifier; static; inline;
@@ -44,6 +49,24 @@ type
     class function GetECSignWithRipeMD160: IDerObjectIdentifier; static; inline;
     class function GetECSignWithSha1: IDerObjectIdentifier; static; inline;
 
+    class function GetBrainpoolP160R1: IDerObjectIdentifier; static; inline;
+    class function GetBrainpoolP160T1: IDerObjectIdentifier; static; inline;
+    class function GetBrainpoolP192R1: IDerObjectIdentifier; static; inline;
+    class function GetBrainpoolP192T1: IDerObjectIdentifier; static; inline;
+    class function GetBrainpoolP224R1: IDerObjectIdentifier; static; inline;
+    class function GetBrainpoolP224T1: IDerObjectIdentifier; static; inline;
+    class function GetBrainpoolP256R1: IDerObjectIdentifier; static; inline;
+    class function GetBrainpoolP256T1: IDerObjectIdentifier; static; inline;
+    class function GetBrainpoolP320R1: IDerObjectIdentifier; static; inline;
+    class function GetBrainpoolP320T1: IDerObjectIdentifier; static; inline;
+    class function GetBrainpoolP384R1: IDerObjectIdentifier; static; inline;
+    class function GetBrainpoolP384T1: IDerObjectIdentifier; static; inline;
+    class function GetBrainpoolP512R1: IDerObjectIdentifier; static; inline;
+    class function GetBrainpoolP512T1: IDerObjectIdentifier; static; inline;
+    class function GetEccBrainpool: IDerObjectIdentifier; static; inline;
+    class function GetEllipticCurve: IDerObjectIdentifier; static; inline;
+    class function GetVersionOne: IDerObjectIdentifier; static; inline;
+
     class constructor TeleTrusTObjectIdentifiers();
 
   public
@@ -58,6 +81,38 @@ type
     class property ECSignWithRipeMD160: IDerObjectIdentifier
       read GetECSignWithRipeMD160;
 
+    class property EccBrainpool: IDerObjectIdentifier read GetEccBrainpool;
+    class property EllipticCurve: IDerObjectIdentifier read GetEllipticCurve;
+    class property VersionOne: IDerObjectIdentifier read GetVersionOne;
+    class property BrainpoolP160R1: IDerObjectIdentifier
+      read GetBrainpoolP160R1;
+    class property BrainpoolP160T1: IDerObjectIdentifier
+      read GetBrainpoolP160T1;
+    class property BrainpoolP192R1: IDerObjectIdentifier
+      read GetBrainpoolP192R1;
+    class property BrainpoolP192T1: IDerObjectIdentifier
+      read GetBrainpoolP192T1;
+    class property BrainpoolP224R1: IDerObjectIdentifier
+      read GetBrainpoolP224R1;
+    class property BrainpoolP224T1: IDerObjectIdentifier
+      read GetBrainpoolP224T1;
+    class property BrainpoolP256R1: IDerObjectIdentifier
+      read GetBrainpoolP256R1;
+    class property BrainpoolP256T1: IDerObjectIdentifier
+      read GetBrainpoolP256T1;
+    class property BrainpoolP320R1: IDerObjectIdentifier
+      read GetBrainpoolP320R1;
+    class property BrainpoolP320T1: IDerObjectIdentifier
+      read GetBrainpoolP320T1;
+    class property BrainpoolP384R1: IDerObjectIdentifier
+      read GetBrainpoolP384R1;
+    class property BrainpoolP384T1: IDerObjectIdentifier
+      read GetBrainpoolP384T1;
+    class property BrainpoolP512R1: IDerObjectIdentifier
+      read GetBrainpoolP512R1;
+    class property BrainpoolP512T1: IDerObjectIdentifier
+      read GetBrainpoolP512T1;
+
     class procedure Boot(); static;
 
   end;
@@ -104,6 +159,107 @@ begin
   result := FRipeMD256;
 end;
 
+class function TTeleTrusTObjectIdentifiers.GetEccBrainpool
+  : IDerObjectIdentifier;
+begin
+  result := FEccBrainpool;
+end;
+
+class function TTeleTrusTObjectIdentifiers.GetVersionOne: IDerObjectIdentifier;
+begin
+  result := FVersionOne;
+end;
+
+class function TTeleTrusTObjectIdentifiers.GetEllipticCurve
+  : IDerObjectIdentifier;
+begin
+  result := FEllipticCurve;
+end;
+
+class function TTeleTrusTObjectIdentifiers.GetBrainpoolP160R1
+  : IDerObjectIdentifier;
+begin
+  result := FBrainpoolP160R1;
+end;
+
+class function TTeleTrusTObjectIdentifiers.GetBrainpoolP160T1
+  : IDerObjectIdentifier;
+begin
+  result := FBrainpoolP160T1;
+end;
+
+class function TTeleTrusTObjectIdentifiers.GetBrainpoolP192R1
+  : IDerObjectIdentifier;
+begin
+  result := FBrainpoolP192R1;
+end;
+
+class function TTeleTrusTObjectIdentifiers.GetBrainpoolP192T1
+  : IDerObjectIdentifier;
+begin
+  result := FBrainpoolP192T1;
+end;
+
+class function TTeleTrusTObjectIdentifiers.GetBrainpoolP224R1
+  : IDerObjectIdentifier;
+begin
+  result := FBrainpoolP224R1;
+end;
+
+class function TTeleTrusTObjectIdentifiers.GetBrainpoolP224T1
+  : IDerObjectIdentifier;
+begin
+  result := FBrainpoolP224T1;
+end;
+
+class function TTeleTrusTObjectIdentifiers.GetBrainpoolP256R1
+  : IDerObjectIdentifier;
+begin
+  result := FBrainpoolP256R1;
+end;
+
+class function TTeleTrusTObjectIdentifiers.GetBrainpoolP256T1
+  : IDerObjectIdentifier;
+begin
+  result := FBrainpoolP256T1;
+end;
+
+class function TTeleTrusTObjectIdentifiers.GetBrainpoolP320R1
+  : IDerObjectIdentifier;
+begin
+  result := FBrainpoolP320R1;
+end;
+
+class function TTeleTrusTObjectIdentifiers.GetBrainpoolP320T1
+  : IDerObjectIdentifier;
+begin
+  result := FBrainpoolP320T1;
+end;
+
+class function TTeleTrusTObjectIdentifiers.GetBrainpoolP384R1
+  : IDerObjectIdentifier;
+begin
+  result := FBrainpoolP384R1;
+end;
+
+class function TTeleTrusTObjectIdentifiers.GetBrainpoolP384T1
+  : IDerObjectIdentifier;
+begin
+  result := FBrainpoolP384T1;
+end;
+
+class function TTeleTrusTObjectIdentifiers.GetBrainpoolP512R1
+  : IDerObjectIdentifier;
+begin
+  result := FBrainpoolP512R1;
+end;
+
+class function TTeleTrusTObjectIdentifiers.GetBrainpoolP512T1
+  : IDerObjectIdentifier;
+begin
+  result := FBrainpoolP512T1;
+end;
+
 class procedure TTeleTrusTObjectIdentifiers.Boot;
 begin
   if not FIsBooted then
@@ -118,6 +274,26 @@ begin
     FECSignWithSha1 := TDerObjectIdentifier.Create(ECSign.ID + '.1');
     FECSignWithRipeMD160 := TDerObjectIdentifier.Create(ECSign.ID + '.2');
 
+    FEccBrainpool := TDerObjectIdentifier.Create(TeleTrusTAlgorithm.ID +
+      '.3.2.8');
+    FEllipticCurve := TDerObjectIdentifier.Create(EccBrainpool.ID + '.1');
+    FVersionOne := TDerObjectIdentifier.Create(EllipticCurve.ID + '.1');
+
+    FBrainpoolP160R1 := TDerObjectIdentifier.Create(VersionOne.ID + '.1');
+    FBrainpoolP160T1 := TDerObjectIdentifier.Create(VersionOne.ID + '.2');
+    FBrainpoolP192R1 := TDerObjectIdentifier.Create(VersionOne.ID + '.3');
+    FBrainpoolP192T1 := TDerObjectIdentifier.Create(VersionOne.ID + '.4');
+    FBrainpoolP224R1 := TDerObjectIdentifier.Create(VersionOne.ID + '.5');
+    FBrainpoolP224T1 := TDerObjectIdentifier.Create(VersionOne.ID + '.6');
+    FBrainpoolP256R1 := TDerObjectIdentifier.Create(VersionOne.ID + '.7');
+    FBrainpoolP256T1 := TDerObjectIdentifier.Create(VersionOne.ID + '.8');
+    FBrainpoolP320R1 := TDerObjectIdentifier.Create(VersionOne.ID + '.9');
+    FBrainpoolP320T1 := TDerObjectIdentifier.Create(VersionOne.ID + '.10');
+    FBrainpoolP384R1 := TDerObjectIdentifier.Create(VersionOne.ID + '.11');
+    FBrainpoolP384T1 := TDerObjectIdentifier.Create(VersionOne.ID + '.12');
+    FBrainpoolP512R1 := TDerObjectIdentifier.Create(VersionOne.ID + '.13');
+    FBrainpoolP512T1 := TDerObjectIdentifier.Create(VersionOne.ID + '.14');
+
     FIsBooted := True;
   end;
 

+ 17 - 49
CryptoLib/src/Asn1/X9/ClpECNamedCurveTable.pas

@@ -24,12 +24,9 @@ interface
 uses
   Generics.Collections,
   ClpCryptoLibTypes,
-  // ClpX962NamedCurves,
-  // ClpECGost3410NamedCurves,
-  // ClpX9ECParameters,
   ClpSecNamedCurves,
   ClpNistNamedCurves,
-  // ClpIECDomainParameters,
+  ClpTeleTrusTNamedCurves,
   ClpIAsn1Objects,
   ClpIX9ECParameters;
 
@@ -42,8 +39,6 @@ type
   strict private
 
     class function GetNames: TCryptoLibStringArray; static;
-    // class function FromDomainParameters(const dp: IECDomainParameters)
-    // : IX9ECParameters; static; inline;
 
   public
     // /**
@@ -55,7 +50,6 @@ type
     // */
     class function GetByName(const name: String): IX9ECParameters; static;
 
-    class function GetName(const oid: IDerObjectIdentifier): String; static;
     // /**
     // * return the object identifier signified by the passed in name. Null
     // * if there is no object identifier associated with name.
@@ -88,36 +82,23 @@ implementation
 
 { TECNamedCurveTable }
 
-// class function TECNamedCurveTable.FromDomainParameters
-// (const dp: IECDomainParameters): IX9ECParameters;
-// begin
-// if dp = Nil then
-// begin
-// result := Nil;
-// end
-// else
-// begin
-// result := TX9ECParameters.Create(dp.Curve, dp.G, dp.N, dp.H, dp.GetSeed())
-// end;
-//
-// end;
-
 class function TECNamedCurveTable.GetByName(const name: String)
   : IX9ECParameters;
 var
   ecP: IX9ECParameters;
 begin
-  // ecP := TX962NamedCurves.GetByName(name);
-  // if (ecP = Nil) then
-  // begin
   ecP := TSecNamedCurves.GetByName(name);
-  // end;
 
   if (ecP = Nil) then
   begin
     ecP := TNistNamedCurves.GetByName(name);
   end;
 
+  if (ecP = Nil) then
+  begin
+    ecP := TTeleTrusTNamedCurves.GetByName(name);
+  end;
+
   result := ecP;
 end;
 
@@ -126,31 +107,15 @@ class function TECNamedCurveTable.GetByOid(const oid: IDerObjectIdentifier)
 var
   ecP: IX9ECParameters;
 begin
-  // ecP := TX962NamedCurves.GetByOid(oid);
-  // if (ecP = Nil) then
-  // begin
   ecP := TSecNamedCurves.GetByOid(oid);
-  // end;
   // NOTE: All the NIST curves are currently from SEC, so no point in redundant OID lookup
-  result := ecP;
-end;
-
-class function TECNamedCurveTable.GetName
-  (const oid: IDerObjectIdentifier): String;
-var
-  name: String;
-begin
-  // name := TX962NamedCurves.GetName(oid);
-  // if (name = '') then
-  // begin
-  name := TSecNamedCurves.GetName(oid);
-  // end;
 
-  if (name = '') then
+  if (ecP = Nil) then
   begin
-    name := TNistNamedCurves.GetName(oid);
+    ecP := TTeleTrusTNamedCurves.GetByOid(oid);
   end;
-  result := name;
+
+  result := ecP;
 end;
 
 class function TECNamedCurveTable.GetOid(const name: String)
@@ -158,17 +123,19 @@ class function TECNamedCurveTable.GetOid(const name: String)
 var
   oid: IDerObjectIdentifier;
 begin
-  // oid := TX962NamedCurves.GetOid(name);
-  // if (oid = Nil) then
-  // begin
+
   oid := TSecNamedCurves.GetOid(name);
-  // end;
 
   if (oid = Nil) then
   begin
     oid := TNistNamedCurves.GetOid(name);
   end;
 
+  if (oid = Nil) then
+  begin
+    oid := TTeleTrusTNamedCurves.GetOid(name);
+  end;
+
   result := oid;
 end;
 
@@ -180,6 +147,7 @@ begin
   try
     temp.AddRange(TSecNamedCurves.Names);
     temp.AddRange(TNistNamedCurves.Names);
+    temp.AddRange(TTeleTrusTNamedCurves.Names);
     result := temp.ToArray;
   finally
     temp.Free;

+ 1 - 1
CryptoLib/src/Crypto/ClpBufferedBlockCipher.pas

@@ -540,7 +540,7 @@ end;
 
 procedure TBufferedBlockCipher.Reset;
 begin
-  TArrayUtils.Fill(Fbuf, 0, System.length(Fbuf), Byte(0));
+  TArrayUtils.ZeroFill(Fbuf);
   FbufOff := 0;
 
   Fcipher.Reset();

+ 44 - 5
CryptoLib/src/Crypto/Digests/ClpDigest.pas

@@ -21,7 +21,9 @@ unit ClpDigest;
 interface
 
 uses
+  SysUtils,
   HlpIHash,
+  HlpIHashInfo,
   ClpIDigest,
   ClpCryptoLibTypes;
 
@@ -44,7 +46,7 @@ type
     function DoFinal: TCryptoLibByteArray; overload;
 
   public
-    constructor Create(const hash: IHash);
+    constructor Create(const hash: IHash; doInitialize: Boolean = True);
 
     /// <summary>
     /// Gets the Underlying <b>IHash</b> Instance
@@ -98,6 +100,11 @@ type
     /// </summary>
     procedure Reset();
 
+    /// <summary>
+    /// Clone the digest instance
+    /// </summary>
+    function Clone(): IDigest;
+
     /// <summary>
     /// the algorithm name
     /// </summary>
@@ -110,8 +117,19 @@ implementation
 { TDigest }
 
 function TDigest.GetAlgorithmName: string;
+var
+  LName: String;
+  LowPoint, HighPoint: Int32;
 begin
-  result := FHash.Name;
+  LName := FHash.Name;
+{$IFDEF DELPHIXE3_UP}
+  LowPoint := System.Low(LName);
+  HighPoint := System.High(LName);
+{$ELSE}
+  LowPoint := 1;
+  HighPoint := System.Length(LName);
+{$ENDIF DELPHIXE3_UP}
+  result := Copy(LName, LowPoint + 1, HighPoint - 1);
 end;
 
 function TDigest.GetByteLength: Int32;
@@ -140,20 +158,35 @@ begin
   FHash.TransformBytes(input, inOff, len);
 end;
 
-constructor TDigest.Create(const hash: IHash);
+constructor TDigest.Create(const hash: IHash; doInitialize: Boolean);
 begin
   Inherited Create();
   FHash := hash;
-  FHash.Initialize;
+  if doInitialize then
+  begin
+    FHash.Initialize;
+  end;
 end;
 
 function TDigest.DoFinal(const output: TCryptoLibByteArray;
   outOff: Int32): Int32;
 var
   buf: TCryptoLibByteArray;
+  Limit, LXOFSizeInBits: Int32;
 begin
 
-  if (System.Length(output) - outOff) < GetDigestSize then
+  if Supports(FHash, IXOF) then
+  begin
+    LXOFSizeInBits := (System.Length(output) - outOff) * 8;
+    (FHash as IXOF).XOFSizeInBits := LXOFSizeInBits;
+    Limit := LXOFSizeInBits shr 3;
+  end
+  else
+  begin
+    Limit := GetDigestSize;
+  end;
+
+  if (System.Length(output) - outOff) < Limit then
   begin
     raise EDataLengthCryptoLibException.CreateRes(@SOutputBufferTooShort);
   end
@@ -163,6 +196,7 @@ begin
     System.Move(buf[0], output[outOff], System.Length(buf) *
       System.SizeOf(Byte));
   end;
+
   result := System.Length(buf);
 end;
 
@@ -176,4 +210,9 @@ begin
   FHash.TransformUntyped(input, System.SizeOf(Byte));
 end;
 
+function TDigest.Clone(): IDigest;
+begin
+  result := TDigest.Create(FHash.Clone(), False);
+end;
+
 end.

+ 4 - 0
CryptoLib/src/Crypto/Engines/ClpAesEngine.pas

@@ -30,6 +30,7 @@ uses
   ClpCheck,
   ClpBits,
   ClpConverters,
+  ClpArrayUtils,
   ClpCryptoLibTypes;
 
 resourcestring
@@ -499,6 +500,7 @@ begin
   keyLen := System.Length(key);
   if ((keyLen < 16) or (keyLen > 32) or ((keyLen and 7) <> 0)) then
   begin
+    TArrayUtils.ZeroFill(key);
     raise EArgumentCryptoLibException.CreateRes(@SInvalidKeyLength);
   end;
 
@@ -676,6 +678,7 @@ begin
       end
   else
     begin
+      TArrayUtils.ZeroFill(key);
       raise EInvalidOperationCryptoLibException.CreateRes(@SInvalidOperation);
     end;
   end;
@@ -696,6 +699,7 @@ begin
 
   result := bigW;
 
+  TArrayUtils.ZeroFill(key);
 end;
 
 function TAesEngine.GetAlgorithmName: String;

+ 4 - 0
CryptoLib/src/Crypto/Engines/ClpAesLightEngine.pas

@@ -30,6 +30,7 @@ uses
   ClpCheck,
   ClpBits,
   ClpConverters,
+  ClpArrayUtils,
   ClpCryptoLibTypes;
 
 resourcestring
@@ -425,6 +426,7 @@ begin
   keyLen := System.Length(key);
   if ((keyLen < 16) or (keyLen > 32) or ((keyLen and 7) <> 0)) then
   begin
+    TArrayUtils.ZeroFill(key);
     raise EArgumentCryptoLibException.CreateRes(@SInvalidKeyLength);
   end;
 
@@ -602,6 +604,7 @@ begin
       end
   else
     begin
+      TArrayUtils.ZeroFill(key);
       raise EInvalidOperationCryptoLibException.CreateRes(@SInvalidOperation);
     end;
   end;
@@ -622,6 +625,7 @@ begin
 
   result := bigW;
 
+  TArrayUtils.ZeroFill(key);
 end;
 
 function TAesLightEngine.GetAlgorithmName: String;

+ 4 - 0
CryptoLib/src/Crypto/Engines/ClpBlowfishEngine.pas

@@ -29,6 +29,7 @@ uses
   ClpIBlowfishEngine,
   ClpCheck,
   ClpConverters,
+  ClpArrayUtils,
   ClpCryptoLibTypes;
 
 resourcestring
@@ -326,6 +327,7 @@ begin
   if ((keyLength < 4) or (keyLength > 56) or (((keyLength * 8) and 7) <> 0))
   then
   begin
+    TArrayUtils.ZeroFill(key);
     raise EArgumentCryptoLibException.CreateRes(@SInvalidKeyLength);
   end;
 
@@ -410,6 +412,8 @@ begin
   ProcessTable(FS0[SBOX_SK - 2], FS0[SBOX_SK - 1], FS1);
   ProcessTable(FS1[SBOX_SK - 2], FS1[SBOX_SK - 1], FS2);
   ProcessTable(FS2[SBOX_SK - 2], FS2[SBOX_SK - 1], FS3);
+
+  TArrayUtils.ZeroFill(key);
 end;
 
 procedure TBlowfishEngine.EncryptBlock(const src: TCryptoLibByteArray;

+ 6 - 0
CryptoLib/src/Crypto/Engines/ClpChaChaEngine.pas

@@ -27,6 +27,7 @@ uses
   ClpIChaChaEngine,
   ClpSalsa20Engine,
   ClpConverters,
+  ClpArrayUtils,
   ClpCryptoLibTypes;
 
 type
@@ -242,6 +243,8 @@ begin
   begin
     if not(Byte(System.Length(keyBytes)) in [16, 32]) then
     begin
+      TArrayUtils.ZeroFill(keyBytes);
+      TArrayUtils.ZeroFill(ivBytes);
       raise EArgumentCryptoLibException.CreateResFmt(@SInvalidKeySize,
         [AlgorithmName]);
     end;
@@ -259,6 +262,9 @@ begin
   // IV
   TConverters.le32_copy(PByte(ivBytes), 0, PCardinal(FEngineState),
     14 * System.SizeOf(UInt32), 2 * System.SizeOf(UInt32));
+
+  TArrayUtils.ZeroFill(keyBytes);
+  TArrayUtils.ZeroFill(ivBytes);
 end;
 
 end.

+ 3 - 3
CryptoLib/src/Crypto/Engines/ClpIESEngine.pas

@@ -442,7 +442,7 @@ begin
     if (FIV <> Nil) then
     begin
       Fcipher.Init(true, TParametersWithIV.Create(TKeyParameter.Create(K1)
-        as IKeyParameter, FIV));
+        as IKeyParameter, FIV) as IParametersWithIV);
     end
     else
     begin
@@ -608,7 +608,7 @@ begin
   if (System.Length(FV) <> 0) then
   begin
     VZ := TArrayUtils.Concatenate(FV, BigZ);
-    TArrayUtils.Fill(BigZ, 0, System.Length(BigZ), Byte(0));
+    TArrayUtils.ZeroFill(BigZ);
     BigZ := VZ;
   end;
 
@@ -629,7 +629,7 @@ begin
     end;
 
   finally
-    TArrayUtils.Fill(BigZ, 0, System.Length(BigZ), Byte(0));
+    TArrayUtils.ZeroFill(BigZ);
   end;
 end;
 

+ 1 - 1
CryptoLib/src/Crypto/Engines/ClpPascalCoinIESEngine.pas

@@ -313,7 +313,7 @@ begin
     end;
 
   finally
-    TArrayUtils.Fill(BigZ, 0, System.Length(BigZ), Byte(0));
+    TArrayUtils.ZeroFill(BigZ);
   end;
 end;
 

+ 5 - 1
CryptoLib/src/Crypto/Engines/ClpRijndaelEngine.pas

@@ -28,6 +28,7 @@ uses
   ClpIRijndaelEngine,
   ClpIKeyParameter,
   ClpICipherParameters,
+  ClpArrayUtils,
   ClpCryptoLibTypes;
 
 resourcestring
@@ -546,6 +547,7 @@ begin
       KC := 8
   else
     begin
+      TArrayUtils.ZeroFill(key);
       raise EArgumentCryptoLibException.CreateRes(@SInvalidKeyLength);
     end;
   end;
@@ -654,6 +656,8 @@ begin
     end;
   end;
   result := W;
+
+  TArrayUtils.ZeroFill(key);
 end;
 
 procedure TRijndaelEngine.PackBlock(const bytes: TCryptoLibByteArray;
@@ -905,7 +909,7 @@ end;
 
 procedure TRijndaelEngine.Reset;
 begin
-
+  // nothing to do.
 end;
 
 end.

+ 11 - 0
CryptoLib/src/Crypto/Engines/ClpSalsa20Engine.pas

@@ -31,6 +31,7 @@ uses
   ClpICipherParameters,
   ClpIParametersWithIV,
   ClpConverters,
+  ClpArrayUtils,
   ClpCryptoLibTypes;
 
 resourcestring
@@ -215,6 +216,7 @@ begin
   iv := ivParams.GetIV();
   if ((iv = Nil) or (System.Length(iv) <> NonceSize)) then
   begin
+    TArrayUtils.ZeroFill(iv);
     raise EArgumentCryptoLibException.CreateResFmt(@SInvalidIV,
       [AlgorithmName, NonceSize]);
   end;
@@ -476,6 +478,8 @@ begin
   begin
     if not(Byte(System.Length(keyBytes)) in [16, 32]) then
     begin
+      TArrayUtils.ZeroFill(keyBytes);
+      TArrayUtils.ZeroFill(ivBytes);
       raise EArgumentCryptoLibException.CreateResFmt(@SInvalidKeySize,
         [AlgorithmName]);
     end;
@@ -497,6 +501,13 @@ begin
   // IV
   TConverters.le32_copy(PByte(ivBytes), 0, PCardinal(FEngineState),
     6 * System.SizeOf(UInt32), 2 * System.SizeOf(UInt32));
+
+  if (Self.ClassType = TSalsa20Engine) then
+  begin
+    TArrayUtils.ZeroFill(keyBytes);
+    TArrayUtils.ZeroFill(ivBytes);
+  end;
+
 end;
 
 end.

+ 48 - 27
CryptoLib/src/Crypto/Engines/ClpSpeckEngine.pas

@@ -28,6 +28,7 @@ uses
   ClpIBlockCipher,
   ClpICipherParameters,
   ClpIKeyParameter,
+  ClpArrayUtils,
   ClpCryptoLibTypes;
 
 resourcestring
@@ -93,10 +94,11 @@ type
     function GetBlockSize(): Int32; virtual;
 
     /// <summary>
-    /// Checks whether a key size provided to the <see cref="ClpSpeckEngine|TSpeckEngine.EngineInit(Boolean,TCryptoLibByteArray)" />
+    /// Checks whether the key size provided to the <see cref="ClpSpeckEngine|TSpeckEngine.EngineInit(Boolean,TCryptoLibByteArray)" />
     /// method is valid.
     /// </summary>
-    procedure CheckKeySize(keySizeBytes: Int32); virtual; abstract;
+    procedure CheckKeySize(const keyBytes: TCryptoLibByteArray);
+      virtual; abstract;
 
     /// <summary>
     /// Sets a key for this cipher instance, calculating the key schedule.
@@ -484,7 +486,7 @@ type
 
   strict protected
     function Mask(val: UInt32): UInt32; override;
-    procedure CheckKeySize(keySizeBytes: Int32); override;
+    procedure CheckKeySize(const keyBytes: TCryptoLibByteArray); override;
 
   public
     constructor Create();
@@ -505,7 +507,7 @@ type
 
   strict protected
     function Mask(val: UInt32): UInt32; override;
-    procedure CheckKeySize(keySizeBytes: Int32); override;
+    procedure CheckKeySize(const keyBytes: TCryptoLibByteArray); override;
 
   public
     constructor Create();
@@ -526,7 +528,7 @@ type
 
   strict protected
     function Mask(val: UInt32): UInt32; override;
-    procedure CheckKeySize(keySizeBytes: Int32); override;
+    procedure CheckKeySize(const keyBytes: TCryptoLibByteArray); override;
 
   public
     constructor Create();
@@ -547,7 +549,7 @@ type
 
   strict protected
     function Mask(val: UInt64): UInt64; override;
-    procedure CheckKeySize(keySizeBytes: Int32); override;
+    procedure CheckKeySize(const keyBytes: TCryptoLibByteArray); override;
 
   public
     constructor Create();
@@ -569,7 +571,7 @@ type
 
   strict protected
     function Mask(val: UInt64): UInt64; override;
-    procedure CheckKeySize(keySizeBytes: Int32); override;
+    procedure CheckKeySize(const keyBytes: TCryptoLibByteArray); override;
 
   public
     constructor Create();
@@ -601,7 +603,7 @@ procedure TSpeckEngine.EngineInit(forEncryption: Boolean;
   const keyBytes: TCryptoLibByteArray);
 begin
   FforEncryption := forEncryption;
-  CheckKeySize(System.Length(keyBytes));
+  CheckKeySize(keyBytes);
   SetKey(keyBytes);
   Finitialised := true;
 end;
@@ -620,7 +622,6 @@ procedure TSpeckEngine.Init(forEncryption: Boolean;
   const parameters: ICipherParameters);
 var
   keyParameter: IKeyParameter;
-  keyBytes: TCryptoLibByteArray;
 begin
 
   if not Supports(parameters, IKeyParameter, keyParameter) then
@@ -628,8 +629,7 @@ begin
     raise EArgumentCryptoLibException.CreateResFmt(@SInvalidParameterSpeckInit,
       [(parameters as TObject).ToString]);
   end;
-  keyBytes := keyParameter.GetKey;
-  EngineInit(forEncryption, keyBytes);
+  EngineInit(forEncryption, keyParameter.GetKey());
 end;
 
 function TSpeckEngine.ProcessBlock(const input: TCryptoLibByteArray;
@@ -817,6 +817,7 @@ begin
 
   end;
 
+  TArrayUtils.ZeroFill(keyBytes);
 end;
 
 { TSpeckUInt64Engine }
@@ -980,6 +981,7 @@ begin
 
   end;
 
+  TArrayUtils.ZeroFill(keyBytes);
 end;
 
 { TSpeck32Engine }
@@ -994,12 +996,16 @@ begin
   result := (val and $FFFF);
 end;
 
-procedure TSpeck32Engine.CheckKeySize(keySizeBytes: Int32);
+procedure TSpeck32Engine.CheckKeySize(const keyBytes: TCryptoLibByteArray);
+var
+  keyBytesSize: Int32;
 begin
-  if (keySizeBytes <> 8) then
+  keyBytesSize := System.Length(keyBytes);
+  if (keyBytesSize <> 8) then
   begin
+    TArrayUtils.ZeroFill(keyBytes);
     raise EArgumentCryptoLibException.CreateResFmt(@SSpeck32InvalidKeySize,
-      [keySizeBytes * 8]);
+      [keyBytesSize * 8]);
   end;
 end;
 
@@ -1015,12 +1021,16 @@ begin
   result := (val and $FFFFFF);
 end;
 
-procedure TSpeck48Engine.CheckKeySize(keySizeBytes: Int32);
+procedure TSpeck48Engine.CheckKeySize(const keyBytes: TCryptoLibByteArray);
+var
+  keyBytesSize: Int32;
 begin
-  if not(keySizeBytes in [9, 12]) then
+  keyBytesSize := System.Length(keyBytes);
+  if not(keyBytesSize in [9, 12]) then
   begin
+    TArrayUtils.ZeroFill(keyBytes);
     raise EArgumentCryptoLibException.CreateResFmt(@SSpeck48InvalidKeySize,
-      [keySizeBytes * 8]);
+      [keyBytesSize * 8]);
   end;
 end;
 
@@ -1036,12 +1046,16 @@ begin
   result := val;
 end;
 
-procedure TSpeck64Engine.CheckKeySize(keySizeBytes: Int32);
+procedure TSpeck64Engine.CheckKeySize(const keyBytes: TCryptoLibByteArray);
+var
+  keyBytesSize: Int32;
 begin
-  if not(keySizeBytes in [12, 16]) then
+  keyBytesSize := System.Length(keyBytes);
+  if not(keyBytesSize in [12, 16]) then
   begin
+    TArrayUtils.ZeroFill(keyBytes);
     raise EArgumentCryptoLibException.CreateResFmt(@SSpeck64InvalidKeySize,
-      [keySizeBytes * 8]);
+      [keyBytesSize * 8]);
   end;
 end;
 
@@ -1057,12 +1071,16 @@ begin
   result := (val and $0000FFFFFFFFFFFF);
 end;
 
-procedure TSpeck96Engine.CheckKeySize(keySizeBytes: Int32);
+procedure TSpeck96Engine.CheckKeySize(const keyBytes: TCryptoLibByteArray);
+var
+  keyBytesSize: Int32;
 begin
-  if not(keySizeBytes in [12, 18]) then
+  keyBytesSize := System.Length(keyBytes);
+  if not(keyBytesSize in [12, 18]) then
   begin
+    TArrayUtils.ZeroFill(keyBytes);
     raise EArgumentCryptoLibException.CreateResFmt(@SSpeck96InvalidKeySize,
-      [keySizeBytes * 8]);
+      [keyBytesSize * 8]);
   end;
 end;
 
@@ -1078,14 +1096,17 @@ begin
   result := val;
 end;
 
-procedure TSpeck128Engine.CheckKeySize(keySizeBytes: Int32);
+procedure TSpeck128Engine.CheckKeySize(const keyBytes: TCryptoLibByteArray);
+var
+  keyBytesSize: Int32;
 begin
-  if not(keySizeBytes in [16, 24, 32]) then
+  keyBytesSize := System.Length(keyBytes);
+  if not(keyBytesSize in [16, 24, 32]) then
   begin
+    TArrayUtils.ZeroFill(keyBytes);
     raise EArgumentCryptoLibException.CreateResFmt(@SSpeck128InvalidKeySize,
-      [keySizeBytes * 8]);
+      [keyBytesSize * 8]);
   end;
 end;
 
 end.
-

+ 53 - 26
CryptoLib/src/Crypto/Engines/ClpSpeckLegacyEngine.pas

@@ -28,6 +28,7 @@ uses
   ClpIBlockCipher,
   ClpICipherParameters,
   ClpIKeyParameter,
+  ClpArrayUtils,
   ClpCryptoLibTypes;
 
 resourcestring
@@ -90,10 +91,11 @@ type
     function GetBlockSize(): Int32; virtual;
 
     /// <summary>
-    /// Checks whether a key size provided to the <see cref="ClpSpeckLegacyEngine|TSpeckLegacyEngine.EngineInit(Boolean,TCryptoLibByteArray)" />
+    /// Checks whether the key size provided to the <see cref="ClpSpeckLegacyEngine|TSpeckLegacyEngine.EngineInit(Boolean,TCryptoLibByteArray)" />
     /// method is valid.
     /// </summary>
-    procedure CheckKeySize(keySizeBytes: Int32); virtual; abstract;
+    procedure CheckKeySize(const keyBytes: TCryptoLibByteArray);
+      virtual; abstract;
 
     /// <summary>
     /// Sets a key for this cipher instance, calculating the key schedule.
@@ -481,7 +483,7 @@ type
 
   strict protected
     function Mask(val: UInt32): UInt32; override;
-    procedure CheckKeySize(keySizeBytes: Int32); override;
+    procedure CheckKeySize(const keyBytes: TCryptoLibByteArray); override;
 
   public
     constructor Create();
@@ -502,7 +504,7 @@ type
 
   strict protected
     function Mask(val: UInt32): UInt32; override;
-    procedure CheckKeySize(keySizeBytes: Int32); override;
+    procedure CheckKeySize(const keyBytes: TCryptoLibByteArray); override;
 
   public
     constructor Create();
@@ -523,7 +525,7 @@ type
 
   strict protected
     function Mask(val: UInt32): UInt32; override;
-    procedure CheckKeySize(keySizeBytes: Int32); override;
+    procedure CheckKeySize(const keyBytes: TCryptoLibByteArray); override;
 
   public
     constructor Create();
@@ -544,7 +546,7 @@ type
 
   strict protected
     function Mask(val: UInt64): UInt64; override;
-    procedure CheckKeySize(keySizeBytes: Int32); override;
+    procedure CheckKeySize(const keyBytes: TCryptoLibByteArray); override;
 
   public
     constructor Create();
@@ -566,7 +568,7 @@ type
 
   strict protected
     function Mask(val: UInt64): UInt64; override;
-    procedure CheckKeySize(keySizeBytes: Int32); override;
+    procedure CheckKeySize(const keyBytes: TCryptoLibByteArray); override;
 
   public
     constructor Create();
@@ -598,7 +600,7 @@ procedure TSpeckLegacyEngine.EngineInit(forEncryption: Boolean;
   const keyBytes: TCryptoLibByteArray);
 begin
   FforEncryption := forEncryption;
-  CheckKeySize(System.Length(keyBytes));
+  CheckKeySize(keyBytes);
   SetKey(keyBytes);
   Finitialised := true;
 end;
@@ -617,7 +619,6 @@ procedure TSpeckLegacyEngine.Init(forEncryption: Boolean;
   const parameters: ICipherParameters);
 var
   keyParameter: IKeyParameter;
-  keyBytes: TCryptoLibByteArray;
 begin
 
   if not Supports(parameters, IKeyParameter, keyParameter) then
@@ -625,8 +626,7 @@ begin
     raise EArgumentCryptoLibException.CreateResFmt
       (@SInvalidParameterSpeckLegacyInit, [(parameters as TObject).ToString]);
   end;
-  keyBytes := keyParameter.GetKey;
-  EngineInit(forEncryption, keyBytes);
+  EngineInit(forEncryption, keyParameter.GetKey());
 end;
 
 function TSpeckLegacyEngine.ProcessBlock(const input: TCryptoLibByteArray;
@@ -817,6 +817,7 @@ begin
 
   end;
 
+  TArrayUtils.ZeroFill(keyBytes);
 end;
 
 { TSpeckUInt64LegacyEngine }
@@ -983,6 +984,7 @@ begin
 
   end;
 
+  TArrayUtils.ZeroFill(keyBytes);
 end;
 
 { TSpeck32LegacyEngine }
@@ -997,12 +999,17 @@ begin
   result := (val and $FFFF);
 end;
 
-procedure TSpeck32LegacyEngine.CheckKeySize(keySizeBytes: Int32);
+procedure TSpeck32LegacyEngine.CheckKeySize(const keyBytes
+  : TCryptoLibByteArray);
+var
+  keyBytesSize: Int32;
 begin
-  if (keySizeBytes <> 8) then
+  keyBytesSize := System.Length(keyBytes);
+  if (keyBytesSize <> 8) then
   begin
+    TArrayUtils.ZeroFill(keyBytes);
     raise EArgumentCryptoLibException.CreateResFmt
-      (@SSpeck32LegacyInvalidKeySize, [keySizeBytes * 8]);
+      (@SSpeck32LegacyInvalidKeySize, [keyBytesSize * 8]);
   end;
 end;
 
@@ -1018,12 +1025,17 @@ begin
   result := (val and $FFFFFF);
 end;
 
-procedure TSpeck48LegacyEngine.CheckKeySize(keySizeBytes: Int32);
+procedure TSpeck48LegacyEngine.CheckKeySize(const keyBytes
+  : TCryptoLibByteArray);
+var
+  keyBytesSize: Int32;
 begin
-  if not(keySizeBytes in [9, 12]) then
+  keyBytesSize := System.Length(keyBytes);
+  if not(keyBytesSize in [9, 12]) then
   begin
+    TArrayUtils.ZeroFill(keyBytes);
     raise EArgumentCryptoLibException.CreateResFmt
-      (@SSpeck48LegacyInvalidKeySize, [keySizeBytes * 8]);
+      (@SSpeck48LegacyInvalidKeySize, [keyBytesSize * 8]);
   end;
 end;
 
@@ -1039,12 +1051,17 @@ begin
   result := val;
 end;
 
-procedure TSpeck64LegacyEngine.CheckKeySize(keySizeBytes: Int32);
+procedure TSpeck64LegacyEngine.CheckKeySize(const keyBytes
+  : TCryptoLibByteArray);
+var
+  keyBytesSize: Int32;
 begin
-  if not(keySizeBytes in [12, 16]) then
+  keyBytesSize := System.Length(keyBytes);
+  if not(keyBytesSize in [12, 16]) then
   begin
+    TArrayUtils.ZeroFill(keyBytes);
     raise EArgumentCryptoLibException.CreateResFmt
-      (@SSpeck64LegacyInvalidKeySize, [keySizeBytes * 8]);
+      (@SSpeck64LegacyInvalidKeySize, [keyBytesSize * 8]);
   end;
 end;
 
@@ -1060,12 +1077,17 @@ begin
   result := (val and $0000FFFFFFFFFFFF);
 end;
 
-procedure TSpeck96LegacyEngine.CheckKeySize(keySizeBytes: Int32);
+procedure TSpeck96LegacyEngine.CheckKeySize(const keyBytes
+  : TCryptoLibByteArray);
+var
+  keyBytesSize: Int32;
 begin
-  if not(keySizeBytes in [12, 18]) then
+  keyBytesSize := System.Length(keyBytes);
+  if not(keyBytesSize in [12, 18]) then
   begin
+    TArrayUtils.ZeroFill(keyBytes);
     raise EArgumentCryptoLibException.CreateResFmt
-      (@SSpeck96LegacyInvalidKeySize, [keySizeBytes * 8]);
+      (@SSpeck96LegacyInvalidKeySize, [keyBytesSize * 8]);
   end;
 end;
 
@@ -1081,12 +1103,17 @@ begin
   result := val;
 end;
 
-procedure TSpeck128LegacyEngine.CheckKeySize(keySizeBytes: Int32);
+procedure TSpeck128LegacyEngine.CheckKeySize(const keyBytes
+  : TCryptoLibByteArray);
+var
+  keyBytesSize: Int32;
 begin
-  if not(keySizeBytes in [16, 24, 32]) then
+  keyBytesSize := System.Length(keyBytes);
+  if not(keyBytesSize in [16, 24, 32]) then
   begin
+    TArrayUtils.ZeroFill(keyBytes);
     raise EArgumentCryptoLibException.CreateResFmt
-      (@SSpeck128LegacyInvalidKeySize, [keySizeBytes * 8]);
+      (@SSpeck128LegacyInvalidKeySize, [keyBytesSize * 8]);
   end;
 end;
 

+ 6 - 0
CryptoLib/src/Crypto/Engines/ClpXSalsa20Engine.pas

@@ -26,6 +26,7 @@ uses
   ClpSalsa20Engine,
   ClpIXSalsa20Engine,
   ClpConverters,
+  ClpArrayUtils,
   ClpCryptoLibTypes;
 
 resourcestring
@@ -79,6 +80,8 @@ begin
 
   if (System.Length(keyBytes) <> 32) then
   begin
+    TArrayUtils.ZeroFill(keyBytes);
+    TArrayUtils.ZeroFill(ivBytes);
     raise EArgumentCryptoLibException.CreateResFmt(@SInvalidKeySize,
       [AlgorithmName]);
   end;
@@ -110,6 +113,9 @@ begin
   TConverters.le32_copy(PByte(ivBytes), 16 * System.SizeOf(Byte),
     PCardinal(FEngineState), 6 * System.SizeOf(UInt32),
     2 * System.SizeOf(UInt32));
+
+  TArrayUtils.ZeroFill(keyBytes);
+  TArrayUtils.ZeroFill(ivBytes);
 end;
 
 end.

+ 265 - 0
CryptoLib/src/Crypto/Generators/ClpArgon2ParametersGenerator.pas

@@ -0,0 +1,265 @@
+{ *********************************************************************************** }
+{ *                              CryptoLib Library                                  * }
+{ *                Copyright (c) 2018 - 20XX Ugochukwu Mmaduekwe                    * }
+{ *                 Github Repository <https://github.com/Xor-el>                   * }
+
+{ *  Distributed under the MIT software license, see the accompanying file LICENSE  * }
+{ *          or visit http://www.opensource.org/licenses/mit-license.php.           * }
+
+{ *                              Acknowledgements:                                  * }
+{ *                                                                                 * }
+{ *      Thanks to Sphere 10 Software (http://www.sphere10.com/) for sponsoring     * }
+{ *                           development of this library                           * }
+
+{ * ******************************************************************************* * }
+
+(* &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&& *)
+
+unit ClpArgon2ParametersGenerator;
+
+{$I ..\..\Include\CryptoLib.inc}
+
+interface
+
+uses
+
+  HlpIHashInfo,
+  HlpHashFactory,
+  HlpPBKDF_Argon2NotBuildInAdapter,
+  ClpPbeParametersGenerator,
+  ClpICipherParameters,
+  ClpIArgon2ParametersGenerator,
+  ClpKeyParameter,
+  ClpIKeyParameter,
+  ClpParametersWithIV,
+  ClpParameterUtilities,
+  ClpArrayUtils,
+  ClpCryptoLibTypes;
+
+resourcestring
+  SArgon2TypeInvalid = 'Selected Argon2Type is Invalid';
+  SArgon2MemoryCostTypeInvalid = 'Selected Argon2MemoryCostType is Invalid';
+
+type
+
+  /// <summary>
+  /// <see href="https://github.com/P-H-C/phc-winner-argon2/blob/master/argon2-specs.pdf">
+  /// Argon2 Specification</see>, <see href="https://tools.ietf.org/html/draft-irtf-cfrg-argon2-04">
+  /// ietf specs</see>
+  /// </summary>
+  TArgon2ParametersGenerator = class sealed(TPbeParametersGenerator,
+    IArgon2ParametersGenerator)
+
+  strict private
+  var
+    FPassword: TCryptoLibByteArray;
+    FPBKDF_Argon2: IPBKDF_Argon2;
+    FArgon2Parameters: IArgon2Parameters;
+
+    function GenerateDerivedKey(dkLen: Int32): TCryptoLibByteArray; inline;
+
+  public
+
+    procedure Clear(); override;
+
+    /// <summary>
+    /// construct an Argon2 Parameters generator.
+    /// </summary>
+    /// <param name="digest">
+    /// digest to use for constructing hmac
+    /// </param>
+    constructor Create();
+
+    destructor Destroy; override;
+
+    procedure Init(argon2Type: TArgon2Type; argon2Version: TArgon2Version;
+      const password, salt, secret, additional: TCryptoLibByteArray;
+      iterations, memory, parallelism: Int32;
+      memoryCostType: TArgon2MemoryCostType);
+
+    /// <summary>
+    /// Generate a key parameter derived from the password, salt, and
+    /// iteration count we are currently initialised with.
+    /// </summary>
+    /// <param name="algorithm">
+    /// a parameters object representing a key.
+    /// </param>
+    /// <param name="keySize">
+    /// the length, in bits, of the key required.
+    /// </param>
+    /// <returns>
+    /// a parameters object representing a key.
+    /// </returns>
+    function GenerateDerivedParameters(const algorithm: String; keySize: Int32)
+      : ICipherParameters; overload; override;
+
+    /// <summary>
+    /// Generate a key with initialisation vector parameter derived from <br />
+    /// the password, salt, and iteration count we are currently initialised
+    /// with.
+    /// </summary>
+    /// <param name="algorithm">
+    /// a parameters object representing a key.
+    /// </param>
+    /// <param name="keySize">
+    /// the length, in bits, of the key required.
+    /// </param>
+    /// <param name="ivSize">
+    /// the length, in bits, of the iv required.
+    /// </param>
+    /// <returns>
+    /// a parameters object representing a key and an iv.
+    /// </returns>
+    function GenerateDerivedParameters(const algorithm: String;
+      keySize, ivSize: Int32): ICipherParameters; overload; override;
+
+    /// <summary>
+    /// Generate a key parameter for use with a MAC derived from the
+    /// password, salt, and iteration count we are currently initialised
+    /// with.
+    /// </summary>
+    /// <param name="keySize">
+    /// the length, in bits, of the key required.
+    /// </param>
+    /// <returns>
+    /// a parameters object representing a key.
+    /// </returns>
+    function GenerateDerivedMacParameters(keySize: Int32)
+      : ICipherParameters; override;
+
+  end;
+
+implementation
+
+{ TArgon2ParametersGenerator }
+
+procedure TArgon2ParametersGenerator.Clear();
+begin
+  TArrayUtils.ZeroFill(FPassword);
+
+  if FArgon2Parameters <> Nil then
+  begin
+    FArgon2Parameters.Clear();
+  end;
+
+  if FPBKDF_Argon2 <> Nil then
+  begin
+    FPBKDF_Argon2.Clear();
+  end;
+end;
+
+constructor TArgon2ParametersGenerator.Create();
+begin
+  Inherited Create();
+end;
+
+destructor TArgon2ParametersGenerator.Destroy();
+begin
+  Clear();
+  inherited Destroy;
+end;
+
+function TArgon2ParametersGenerator.GenerateDerivedKey(dkLen: Int32)
+  : TCryptoLibByteArray;
+begin
+  result := FPBKDF_Argon2.GetBytes(dkLen);
+end;
+
+function TArgon2ParametersGenerator.GenerateDerivedMacParameters(keySize: Int32)
+  : ICipherParameters;
+var
+  dKey: TCryptoLibByteArray;
+begin
+  keySize := keySize div 8;
+
+  dKey := GenerateDerivedKey(keySize);
+
+  result := TKeyParameter.Create(dKey, 0, keySize);
+end;
+
+function TArgon2ParametersGenerator.GenerateDerivedParameters(const algorithm
+  : String; keySize: Int32): ICipherParameters;
+var
+  dKey: TCryptoLibByteArray;
+begin
+  keySize := keySize div 8;
+
+  dKey := GenerateDerivedKey(keySize);
+
+  result := TParameterUtilities.CreateKeyParameter(algorithm, dKey, 0, keySize);
+end;
+
+function TArgon2ParametersGenerator.GenerateDerivedParameters(const algorithm
+  : String; keySize, ivSize: Int32): ICipherParameters;
+var
+  dKey: TCryptoLibByteArray;
+  key: IKeyParameter;
+begin
+  keySize := keySize div 8;
+  ivSize := ivSize div 8;
+
+  dKey := GenerateDerivedKey(keySize + ivSize);
+  key := TParameterUtilities.CreateKeyParameter(algorithm, dKey, 0, keySize);
+
+  result := TParametersWithIV.Create(key, dKey, keySize, ivSize);
+end;
+
+procedure TArgon2ParametersGenerator.Init(argon2Type: TArgon2Type;
+  argon2Version: TArgon2Version; const password, salt, secret,
+  additional: TCryptoLibByteArray; iterations, memory, parallelism: Int32;
+  memoryCostType: TArgon2MemoryCostType);
+var
+  LArgon2ParametersBuilder: IArgon2ParametersBuilder;
+begin
+  FPassword := System.Copy(password);
+
+  case argon2Type of
+    TArgon2Type.a2tARGON2_d:
+      begin
+        LArgon2ParametersBuilder := TArgon2dParametersBuilder.Builder();
+      end;
+
+    TArgon2Type.a2tARGON2_i:
+      begin
+        LArgon2ParametersBuilder := TArgon2iParametersBuilder.Builder();
+      end;
+    TArgon2Type.a2tARGON2_id:
+      begin
+        LArgon2ParametersBuilder := TArgon2idParametersBuilder.Builder();
+      end
+  else
+    begin
+      raise EArgumentCryptoLibException.CreateRes(@SArgon2TypeInvalid);
+    end;
+  end;
+
+  case memoryCostType of
+    TArgon2MemoryCostType.a2mctMemoryAsKB:
+      begin
+        LArgon2ParametersBuilder.WithVersion(argon2Version).WithSalt(salt)
+          .WithSecret(secret).WithAdditional(additional)
+          .WithIterations(iterations).WithMemoryAsKB(memory)
+          .WithParallelism(parallelism);
+      end;
+
+    TArgon2MemoryCostType.a2mctMemoryPowOfTwo:
+      begin
+        LArgon2ParametersBuilder.WithVersion(argon2Version).WithSalt(salt)
+          .WithSecret(secret).WithAdditional(additional)
+          .WithIterations(iterations).WithMemoryPowOfTwo(memory)
+          .WithParallelism(parallelism);
+      end
+  else
+    begin
+      raise EArgumentCryptoLibException.CreateRes
+        (@SArgon2MemoryCostTypeInvalid);
+    end;
+  end;
+
+  FArgon2Parameters := LArgon2ParametersBuilder.Build();
+  LArgon2ParametersBuilder.Clear();
+  FPBKDF_Argon2 := TKDF.TPBKDF_Argon2.CreatePBKDF_Argon2(FPassword,
+    FArgon2Parameters);
+end;
+
+end.

+ 63 - 0
CryptoLib/src/Crypto/Generators/ClpKdf1BytesGenerator.pas

@@ -0,0 +1,63 @@
+{ *********************************************************************************** }
+{ *                              CryptoLib Library                                  * }
+{ *                Copyright (c) 2018 - 20XX Ugochukwu Mmaduekwe                    * }
+{ *                 Github Repository <https://github.com/Xor-el>                   * }
+
+{ *  Distributed under the MIT software license, see the accompanying file LICENSE  * }
+{ *          or visit http://www.opensource.org/licenses/mit-license.php.           * }
+
+{ *                              Acknowledgements:                                  * }
+{ *                                                                                 * }
+{ *      Thanks to Sphere 10 Software (http://www.sphere10.com/) for sponsoring     * }
+{ *                           development of this library                           * }
+
+{ * ******************************************************************************* * }
+
+(* &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&& *)
+
+unit ClpKdf1BytesGenerator;
+
+{$I ..\..\Include\CryptoLib.inc}
+
+interface
+
+uses
+  ClpIDigest,
+  ClpBaseKdfBytesGenerator,
+  ClpIKdf1BytesGenerator;
+
+type
+
+  /// <summary>
+  /// <para>
+  /// KDF1 generator for derived keys and ivs as defined by IEEE
+  /// P1363a/ISO 18033
+  /// </para>
+  /// <para>
+  /// This implementation is based on IEEE P1363/ISO 18033.
+  /// </para>
+  /// </summary>
+  TKdf1BytesGenerator = class(TBaseKdfBytesGenerator, IKdf1BytesGenerator)
+
+  public
+
+    /// <summary>
+    /// Construct a KDF1 bytes generator.
+    /// </summary>
+    /// <param name="digest">
+    /// the digest to be used as the source of derived keys.
+    /// </param>
+    constructor Create(const digest: IDigest);
+
+  end;
+
+implementation
+
+{ TKdf1BytesGenerator }
+
+constructor TKdf1BytesGenerator.Create(const digest: IDigest);
+begin
+  Inherited Create(0, digest);
+end;
+
+end.

+ 2 - 83
CryptoLib/src/Crypto/Generators/ClpPbeParametersGenerator.pas

@@ -23,13 +23,7 @@ interface
 
 uses
   ClpICipherParameters,
-  ClpIPbeParametersGenerator,
-  ClpCryptoLibTypes;
-
-resourcestring
-  SEmptyPassword = 'Password can''t be empty';
-  SEmptySalt = 'Salt can''t be empty';
-  SIterationtooSmall = 'Iteration must be greater than zero.';
+  ClpIPbeParametersGenerator;
 
 type
 
@@ -40,45 +34,9 @@ type
   TPbeParametersGenerator = class abstract(TInterfacedObject,
     IPbeParametersGenerator)
 
-  strict protected
-  var
-    FmPassword, FmSalt: TCryptoLibByteArray;
-    FmIterationCount: Int32;
-
-    /// <returns>
-    /// the password byte array.
-    /// </returns>
-    function GetPassword: TCryptoLibByteArray; virtual;
-
-    /// <returns>
-    /// the salt byte array.
-    /// </returns>
-    function GetSalt: TCryptoLibByteArray; virtual;
-
-    /// <returns>
-    /// the iteration count.
-    /// </returns>
-    function GetIterationCount: Int32; virtual;
-
   public
 
-    procedure Init(const password, salt: TCryptoLibByteArray;
-      iterationCount: Int32); virtual;
-
-    /// <value>
-    /// the password byte array.
-    /// </value>
-    property password: TCryptoLibByteArray read GetPassword;
-
-    /// <value>
-    /// the salt byte array.
-    /// </value>
-    property salt: TCryptoLibByteArray read GetSalt;
-
-    /// <value>
-    /// the iteration count.
-    /// </value>
-    property iterationCount: Int32 read GetIterationCount;
+    procedure Clear(); virtual; abstract;
 
     /// <summary>
     /// Generate derived parameters for a key of length keySize.
@@ -131,43 +89,4 @@ type
 
 implementation
 
-{ TPbeParametersGenerator }
-
-function TPbeParametersGenerator.GetIterationCount: Int32;
-begin
-  result := FmIterationCount;
-end;
-
-function TPbeParametersGenerator.GetPassword: TCryptoLibByteArray;
-begin
-  result := System.Copy(FmPassword);
-end;
-
-function TPbeParametersGenerator.GetSalt: TCryptoLibByteArray;
-begin
-  result := System.Copy(FmSalt);
-end;
-
-procedure TPbeParametersGenerator.Init(const password,
-  salt: TCryptoLibByteArray; iterationCount: Int32);
-begin
-
-  if (password = Nil) then
-  begin
-    raise EArgumentNilCryptoLibException.CreateRes(@SEmptyPassword);
-  end;
-
-  if (salt = Nil) then
-  begin
-    raise EArgumentNilCryptoLibException.CreateRes(@SEmptySalt);
-  end;
-
-  if (iterationCount < 1) then
-    raise EArgumentCryptoLibException.CreateRes(@SIterationtooSmall);
-
-  FmPassword := System.Copy(password);
-  FmSalt := System.Copy(salt);
-  FmIterationCount := iterationCount;
-end;
-
 end.

+ 28 - 5
CryptoLib/src/Crypto/Generators/ClpPkcs5S2ParametersGenerator.pas

@@ -33,6 +33,7 @@ uses
   ClpParametersWithIV,
   ClpParameterUtilities,
   ClpPbeParametersGenerator,
+  ClpArrayUtils,
   ClpCryptoLibTypes;
 
 type
@@ -46,6 +47,7 @@ type
 
   strict private
   var
+    FPassword, FSalt: TCryptoLibByteArray;
     Fdigest: IDigest;
     FPBKDF2_HMAC: HlpIHashInfo.IPBKDF2_HMAC;
 
@@ -58,6 +60,7 @@ type
 
   public
 
+    procedure Clear(); override;
     /// <summary>
     /// construct a Pkcs5 Scheme 2 Parameters generator.
     /// </summary>
@@ -66,8 +69,10 @@ type
     /// </param>
     constructor Create(const digest: IDigest);
 
+    destructor Destroy; override;
+
     procedure Init(const password, salt: TCryptoLibByteArray;
-      iterationCount: Int32); override;
+      iterationCount: Int32);
 
     /// <summary>
     /// Generate a key parameter derived from the password, salt, and
@@ -116,8 +121,8 @@ type
     /// <returns>
     /// a parameters object representing a key.
     /// </returns>
-    function GenerateDerivedMacParameters(keySize: Int32): ICipherParameters;
-      overload; override;
+    function GenerateDerivedMacParameters(keySize: Int32)
+      : ICipherParameters; override;
 
     /// <value>
     /// the underlying digest.
@@ -129,12 +134,29 @@ implementation
 
 { TPkcs5S2ParametersGenerator }
 
+procedure TPkcs5S2ParametersGenerator.Clear();
+begin
+  TArrayUtils.ZeroFill(FPassword);
+  TArrayUtils.ZeroFill(FSalt);
+
+  if FPBKDF2_HMAC <> Nil then
+  begin
+    FPBKDF2_HMAC.Clear();
+  end;
+end;
+
 constructor TPkcs5S2ParametersGenerator.Create(const digest: IDigest);
 begin
   Inherited Create();
   Fdigest := digest;
 end;
 
+destructor TPkcs5S2ParametersGenerator.Destroy;
+begin
+  Clear();
+  inherited Destroy;
+end;
+
 function TPkcs5S2ParametersGenerator.GenerateDerivedKey(dkLen: Int32)
   : TCryptoLibByteArray;
 begin
@@ -188,9 +210,10 @@ end;
 procedure TPkcs5S2ParametersGenerator.Init(const password,
   salt: TCryptoLibByteArray; iterationCount: Int32);
 begin
-  inherited Init(password, salt, iterationCount);
+  FPassword := System.Copy(password);
+  FSalt := System.Copy(salt);
   FPBKDF2_HMAC := TKDF.TPBKDF2_HMAC.CreatePBKDF2_HMAC
-    (Fdigest.GetUnderlyingIHash, password, salt, iterationCount);
+    (Fdigest.GetUnderlyingIHash, FPassword, FSalt, iterationCount);
 end;
 
 end.

+ 199 - 0
CryptoLib/src/Crypto/Generators/ClpScryptParametersGenerator.pas

@@ -0,0 +1,199 @@
+{ *********************************************************************************** }
+{ *                              CryptoLib Library                                  * }
+{ *                Copyright (c) 2018 - 20XX Ugochukwu Mmaduekwe                    * }
+{ *                 Github Repository <https://github.com/Xor-el>                   * }
+
+{ *  Distributed under the MIT software license, see the accompanying file LICENSE  * }
+{ *          or visit http://www.opensource.org/licenses/mit-license.php.           * }
+
+{ *                              Acknowledgements:                                  * }
+{ *                                                                                 * }
+{ *      Thanks to Sphere 10 Software (http://www.sphere10.com/) for sponsoring     * }
+{ *                           development of this library                           * }
+
+{ * ******************************************************************************* * }
+
+(* &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&& *)
+
+unit ClpScryptParametersGenerator;
+
+{$I ..\..\Include\CryptoLib.inc}
+
+interface
+
+uses
+
+  HlpIHashInfo,
+  HlpHashFactory,
+  ClpICipherParameters,
+  ClpPbeParametersGenerator,
+  ClpIScryptParametersGenerator,
+  ClpKeyParameter,
+  ClpIKeyParameter,
+  ClpParametersWithIV,
+  ClpParameterUtilities,
+  ClpArrayUtils,
+  ClpCryptoLibTypes;
+
+type
+
+  /// <summary>
+  /// <a href="http://tools.ietf.org/html/draft-josefsson-scrypt-kdf-01">draft-josefsson-scrypt-kd</a>
+  /// Scrypt Specification</see>
+  /// </summary>
+  TScryptParametersGenerator = class sealed(TPbeParametersGenerator,
+    IScryptParametersGenerator)
+
+  strict private
+  var
+    FPassword, FSalt: TCryptoLibByteArray;
+    FPBKDF_Scrypt: HlpIHashInfo.IPBKDF_Scrypt;
+
+    function GenerateDerivedKey(dkLen: Int32): TCryptoLibByteArray; inline;
+
+  public
+
+    procedure Clear(); override;
+    /// <summary>
+    /// construct an Scrypt Parameters generator.
+    /// </summary>
+    constructor Create();
+
+    destructor Destroy; override;
+
+    procedure Init(const password, salt: TCryptoLibByteArray;
+      cost, blockSize, parallelism: Int32);
+
+    /// <summary>
+    /// Generate a key parameter derived from the password, salt,
+    /// cost, blockSize, parallelism we are currently initialised with.
+    /// </summary>
+    /// <param name="algorithm">
+    /// a parameters object representing a key.
+    /// </param>
+    /// <param name="keySize">
+    /// the length, in bits, of the key required.
+    /// </param>
+    /// <returns>
+    /// a parameters object representing a key.
+    /// </returns>
+    function GenerateDerivedParameters(const algorithm: String; keySize: Int32)
+      : ICipherParameters; overload; override;
+
+    /// <summary>
+    /// Generate a key with initialisation vector parameter derived from <br />
+    /// the password, salt, cost, blockSize, parallelism we are currently initialised with.
+    /// </summary>
+    /// </summary>
+    /// <param name="algorithm">
+    /// a parameters object representing a key.
+    /// </param>
+    /// <param name="keySize">
+    /// the length, in bits, of the key required.
+    /// </param>
+    /// <param name="ivSize">
+    /// the length, in bits, of the iv required.
+    /// </param>
+    /// <returns>
+    /// a parameters object representing a key and an iv.
+    /// </returns>
+    function GenerateDerivedParameters(const algorithm: String;
+      keySize, ivSize: Int32): ICipherParameters; overload; override;
+
+    /// <summary>
+    /// Generate a key parameter for use with a MAC derived from the
+    /// the password, salt, cost, blockSize, parallelism we are currently initialised with.
+    /// with.
+    /// </summary>
+    /// <param name="keySize">
+    /// the length, in bits, of the key required.
+    /// </param>
+    /// <returns>
+    /// a parameters object representing a key.
+    /// </returns>
+    function GenerateDerivedMacParameters(keySize: Int32)
+      : ICipherParameters; override;
+
+  end;
+
+implementation
+
+{ TPkcs5S2ParametersGenerator }
+
+procedure TScryptParametersGenerator.Clear();
+begin
+  TArrayUtils.ZeroFill(FPassword);
+  TArrayUtils.ZeroFill(FSalt);
+
+  if FPBKDF_Scrypt <> Nil then
+  begin
+    FPBKDF_Scrypt.Clear();
+  end;
+end;
+
+constructor TScryptParametersGenerator.Create();
+begin
+  Inherited Create();
+end;
+
+destructor TScryptParametersGenerator.Destroy;
+begin
+  Clear();
+  inherited Destroy;
+end;
+
+function TScryptParametersGenerator.GenerateDerivedKey(dkLen: Int32)
+  : TCryptoLibByteArray;
+begin
+  result := FPBKDF_Scrypt.GetBytes(dkLen);
+end;
+
+function TScryptParametersGenerator.GenerateDerivedMacParameters(keySize: Int32)
+  : ICipherParameters;
+var
+  dKey: TCryptoLibByteArray;
+begin
+  keySize := keySize div 8;
+
+  dKey := GenerateDerivedKey(keySize);
+
+  result := TKeyParameter.Create(dKey, 0, keySize);
+end;
+
+function TScryptParametersGenerator.GenerateDerivedParameters(const algorithm
+  : String; keySize: Int32): ICipherParameters;
+var
+  dKey: TCryptoLibByteArray;
+begin
+  keySize := keySize div 8;
+
+  dKey := GenerateDerivedKey(keySize);
+
+  result := TParameterUtilities.CreateKeyParameter(algorithm, dKey, 0, keySize);
+end;
+
+function TScryptParametersGenerator.GenerateDerivedParameters(const algorithm
+  : String; keySize, ivSize: Int32): ICipherParameters;
+var
+  dKey: TCryptoLibByteArray;
+  key: IKeyParameter;
+begin
+  keySize := keySize div 8;
+  ivSize := ivSize div 8;
+
+  dKey := GenerateDerivedKey(keySize + ivSize);
+  key := TParameterUtilities.CreateKeyParameter(algorithm, dKey, 0, keySize);
+
+  result := TParametersWithIV.Create(key, dKey, keySize, ivSize);
+end;
+
+procedure TScryptParametersGenerator.Init(const password,
+  salt: TCryptoLibByteArray; cost, blockSize, parallelism: Int32);
+begin
+  FPassword := System.Copy(password);
+  FSalt := System.Copy(salt);
+  FPBKDF_Scrypt := TKDF.TPBKDF_Scrypt.CreatePBKDF_Scrypt(FPassword, FSalt, cost,
+    blockSize, parallelism);
+end;
+
+end.

+ 15 - 0
CryptoLib/src/Crypto/Macs/ClpHMac.pas

@@ -57,6 +57,10 @@ type
   public
     constructor Create(const digest: IDigest);
 
+    destructor Destroy(); override;
+
+    procedure Clear();
+
     function GetUnderlyingDigest: IDigest; inline;
     function GetMacSize: Int32; inline;
 
@@ -91,6 +95,11 @@ begin
   FHMAC.TransformBytes(input, inOff, len);
 end;
 
+procedure THMac.Clear();
+begin
+  FHMAC.Clear();
+end;
+
 constructor THMac.Create(const digest: IDigest);
 begin
   Inherited Create();
@@ -98,6 +107,12 @@ begin
   FHMAC := THashFactory.THMac.CreateHMAC(FDigest.GetUnderlyingIHash);
 end;
 
+destructor THMac.Destroy;
+begin
+  Clear();
+  inherited Destroy;
+end;
+
 function THMac.DoFinal(const output: TCryptoLibByteArray; outOff: Int32): Int32;
 var
   buf: TCryptoLibByteArray;

+ 2 - 2
CryptoLib/src/Crypto/Modes/ClpBlockCipherModes.pas

@@ -789,7 +789,7 @@ end;
 procedure TCbcBlockCipher.Reset;
 begin
   System.Move(FIV[0], FcbcV[0], System.Length(FIV));
-  TArrayUtils.Fill(FcbcNextV, 0, System.Length(FcbcNextV), Byte(0));
+  TArrayUtils.ZeroFill(FcbcNextV);
 
   Fcipher.Reset();
 end;
@@ -1179,7 +1179,7 @@ end;
 
 procedure TSicBlockCipher.Reset;
 begin
-  TArrayUtils.Fill(Fcounter, 0, System.Length(Fcounter), Byte(0));
+  TArrayUtils.ZeroFill(Fcounter);
   System.Move(FIV[0], Fcounter[0], System.Length(FIV) * System.SizeOf(Byte));
 
   Fcipher.Reset();

+ 0 - 1
CryptoLib/src/Crypto/Paddings/ClpPaddedBufferedBlockCipher.pas

@@ -322,7 +322,6 @@ begin
 
   if (leftOver = 0) then
   begin
-    // result := total - System.length(Fbuf);
     result := Max(0, total - System.length(Fbuf));
     Exit;
   end;

+ 0 - 17
CryptoLib/src/Crypto/Paddings/ClpPaddingModes.pas

@@ -532,23 +532,6 @@ var
   count, i: Int32;
   failed: Boolean;
 begin
-  // countAsByte := input[System.Length(input) - 1];
-  // count := countAsByte;
-  //
-  // if ((count < 1) or (count > System.Length(input))) then
-  // begin
-  // raise EInvalidCipherTextCryptoLibException.CreateRes(@SCorruptedPadBlock);
-  // end;
-  //
-  // for i := 2 to count do
-  // begin
-  // if (input[System.Length(input) - i] <> countAsByte) then
-  // begin
-  // raise EInvalidCipherTextCryptoLibException.CreateRes(@SCorruptedPadBlock);
-  // end;
-  // end;
-  //
-  // result := count;
 
   count := input[System.Length(input) - 1] and $FF;
   countAsByte := Byte(count);

+ 1 - 5
CryptoLib/src/Crypto/Parameters/ClpHkdfParameters.pas

@@ -153,11 +153,7 @@ begin
     Fsalt := System.Copy(salt);
   end;
 
-  if (info = Nil) then
-  begin
-    System.SetLength(Finfo, 0);
-  end
-  else
+  if info <> Nil then
   begin
     Finfo := System.Copy(info);
   end;

+ 7 - 1
CryptoLib/src/Crypto/Parameters/ClpKeyParameter.pas

@@ -46,6 +46,7 @@ type
       keyOff, keyLen: Int32); overload;
     destructor Destroy; override;
     function GetKey(): TCryptoLibByteArray; inline;
+    procedure Clear(); inline;
 
   end;
 
@@ -64,6 +65,11 @@ begin
   Fkey := System.Copy(key);
 end;
 
+procedure TKeyParameter.Clear;
+begin
+  TArrayUtils.ZeroFill(Fkey);
+end;
+
 constructor TKeyParameter.Create(const key: TCryptoLibByteArray;
   keyOff, keyLen: Int32);
 begin
@@ -91,7 +97,7 @@ end;
 
 destructor TKeyParameter.Destroy;
 begin
-  TArrayUtils.Fill(Fkey, 0, System.Length(Fkey), Byte(0));
+  Clear();
   inherited Destroy;
 end;
 

+ 7 - 1
CryptoLib/src/Crypto/Parameters/ClpParametersWithIV.pas

@@ -49,6 +49,7 @@ type
     destructor Destroy; override;
     function GetIV(): TCryptoLibByteArray; inline;
     property parameters: ICipherParameters read GetParameters;
+    procedure Clear(); inline;
 
   end;
 
@@ -63,6 +64,11 @@ begin
   Create(parameters, iv, 0, System.Length(iv))
 end;
 
+procedure TParametersWithIV.Clear;
+begin
+  TArrayUtils.ZeroFill(Fiv);
+end;
+
 constructor TParametersWithIV.Create(const parameters: ICipherParameters;
   const iv: TCryptoLibByteArray; ivOff, ivLen: Int32);
 begin
@@ -79,7 +85,7 @@ end;
 
 destructor TParametersWithIV.Destroy;
 begin
-  TArrayUtils.Fill(Fiv, 0, System.Length(Fiv), Byte(0));
+  Clear();
   inherited Destroy;
 end;
 

+ 1 - 1
CryptoLib/src/Crypto/Prng/ClpDigestRandomGenerator.pas

@@ -186,7 +186,7 @@ procedure TDigestRandomGenerator.NextBytes(const bytes: TCryptoLibByteArray;
   start, len: Int32);
 var
   stateOff, endPoint: Int32;
-  I: Integer;
+  I: Int32;
 begin
 
   FLock.Acquire;

+ 0 - 1
CryptoLib/src/Crypto/Signers/ClpECNRSigner.pas

@@ -167,7 +167,6 @@ begin
 
     tempPair := keyGen.GenerateKeyPair();
 
-    // BigInteger Vx := tempPair.getPublic().getW().getAffineX();
     V := tempPair.Public as IECPublicKeyParameters; // get temp's public key
     Vx := V.Q.AffineXCoord.ToBigInteger(); // get the point's x coordinate
 

+ 5 - 0
CryptoLib/src/Crypto/Signers/ClpEd25519Blake2BSigner.pas

@@ -172,6 +172,11 @@ begin
     raise EInvalidOperationCryptoLibException.CreateRes
       (@SNotInitializedForVerifying);
   end;
+  if (TEd25519Blake2B.SignatureSize <> System.Length(signature)) then
+  begin
+    Result := false;
+    Exit;
+  end;
   pk := FPublicKey.GetEncoded();
   buf := Aggregate();
   count := System.Length(buf);

+ 5 - 0
CryptoLib/src/Crypto/Signers/ClpEd25519CtxBlake2BSigner.pas

@@ -174,6 +174,11 @@ begin
     raise EInvalidOperationCryptoLibException.CreateRes
       (@SNotInitializedForVerifying);
   end;
+  if (TEd25519Blake2B.SignatureSize <> System.Length(signature)) then
+  begin
+    Result := false;
+    Exit;
+  end;
   pk := FPublicKey.GetEncoded();
   buf := Aggregate();
   count := System.Length(buf);

+ 5 - 0
CryptoLib/src/Crypto/Signers/ClpEd25519CtxSigner.pas

@@ -173,6 +173,11 @@ begin
     raise EInvalidOperationCryptoLibException.CreateRes
       (@SNotInitializedForVerifying);
   end;
+  if (TEd25519.SignatureSize <> System.Length(signature)) then
+  begin
+    Result := false;
+    Exit;
+  end;
   pk := FPublicKey.GetEncoded();
   buf := Aggregate();
   count := System.Length(buf);

+ 5 - 0
CryptoLib/src/Crypto/Signers/ClpEd25519PhBlake2BSigner.pas

@@ -165,6 +165,11 @@ begin
     raise EInvalidOperationCryptoLibException.CreateRes
       (@SNotInitializedForVerifying);
   end;
+  if (TEd25519Blake2B.SignatureSize <> System.Length(signature)) then
+  begin
+    Result := false;
+    Exit;
+  end;
   pk := FPublicKey.GetEncoded();
   Result := FEd25519Blake2BInstance.VerifyPrehash(signature, 0, pk, 0, FContext,
     FPreHash);

+ 5 - 0
CryptoLib/src/Crypto/Signers/ClpEd25519PhSigner.pas

@@ -164,6 +164,11 @@ begin
     raise EInvalidOperationCryptoLibException.CreateRes
       (@SNotInitializedForVerifying);
   end;
+  if (TEd25519.SignatureSize <> System.Length(signature)) then
+  begin
+    Result := false;
+    Exit;
+  end;
   pk := FPublicKey.GetEncoded();
   Result := FEd25519Instance.VerifyPrehash(signature, 0, pk, 0, FContext,
     FPreHash);

+ 5 - 0
CryptoLib/src/Crypto/Signers/ClpEd25519Signer.pas

@@ -171,6 +171,11 @@ begin
     raise EInvalidOperationCryptoLibException.CreateRes
       (@SNotInitializedForVerifying);
   end;
+  if (TEd25519.SignatureSize <> System.Length(signature)) then
+  begin
+    Result := false;
+    Exit;
+  end;
   pk := FPublicKey.GetEncoded();
   buf := Aggregate();
   count := System.Length(buf);

+ 1 - 1
CryptoLib/src/Crypto/Signers/ClpHMacDsaKCalculator.pas

@@ -128,7 +128,7 @@ var
 begin
   Fn := n;
   TArrayUtils.Fill(FV, 0, System.Length(FV), Byte($01));
-  TArrayUtils.Fill(FK, 0, System.Length(FK), Byte(0));
+  TArrayUtils.ZeroFill(FK);
 
   size := TBigIntegers.GetUnsignedByteLength(n);
   System.SetLength(x, size);

+ 1 - 1
CryptoLib/src/Crypto/Signers/SignersEncodings/ClpSignersEncodings.pas

@@ -17,7 +17,7 @@
 
 unit ClpSignersEncodings;
 
-{$I ..\..\Include\CryptoLib.inc}
+{$I ..\..\..\Include\CryptoLib.inc}
 
 interface
 

+ 50 - 0
CryptoLib/src/Interfaces/ClpIArgon2ParametersGenerator.pas

@@ -0,0 +1,50 @@
+{ *********************************************************************************** }
+{ *                              CryptoLib Library                                  * }
+{ *                Copyright (c) 2018 - 20XX Ugochukwu Mmaduekwe                    * }
+{ *                 Github Repository <https://github.com/Xor-el>                   * }
+
+{ *  Distributed under the MIT software license, see the accompanying file LICENSE  * }
+{ *          or visit http://www.opensource.org/licenses/mit-license.php.           * }
+
+{ *                              Acknowledgements:                                  * }
+{ *                                                                                 * }
+{ *      Thanks to Sphere 10 Software (http://www.sphere10.com/) for sponsoring     * }
+{ *                           development of this library                           * }
+
+{ * ******************************************************************************* * }
+
+(* &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&& *)
+
+unit ClpIArgon2ParametersGenerator;
+
+{$I ..\Include\CryptoLib.inc}
+
+interface
+
+uses
+  HlpArgon2TypeAndVersion,
+  ClpIPbeParametersGenerator,
+  ClpCryptoLibTypes;
+
+type
+{$SCOPEDENUMS ON}
+  TArgon2Type = HlpArgon2TypeAndVersion.TArgon2Type;
+  TArgon2Version = HlpArgon2TypeAndVersion.TArgon2Version;
+  TArgon2MemoryCostType = (a2mctMemoryAsKB, a2mctMemoryPowOfTwo);
+{$SCOPEDENUMS OFF}
+
+type
+  IArgon2ParametersGenerator = interface(IPbeParametersGenerator)
+
+    ['{0AC3D3A8-9422-405F-B0EE-6B7AE0F64F74}']
+
+    procedure Init(argon2Type: TArgon2Type; argon2Version: TArgon2Version;
+      const password, salt, secret, additional: TCryptoLibByteArray;
+      iterations, memory, parallelism: Int32;
+      memoryCostType: TArgon2MemoryCostType);
+
+  end;
+
+implementation
+
+end.

+ 2 - 2
CryptoLib/src/Interfaces/ClpIAsn1Objects.pas

@@ -207,7 +207,7 @@ type
 
     function GetCount: Int32;
     function GetParser: IAsn1SequenceParser;
-    function GetSelf(Index: Integer): IAsn1Encodable;
+    function GetSelf(Index: Int32): IAsn1Encodable;
     function GetCurrent(const e: IAsn1Encodable): IAsn1Encodable;
 
     procedure AddObject(const obj: IAsn1Encodable);
@@ -294,7 +294,7 @@ type
 
     function GetCount: Int32;
     function GetParser: IAsn1SetParser;
-    function GetSelf(Index: Integer): IAsn1Encodable;
+    function GetSelf(Index: Int32): IAsn1Encodable;
     function GetCurrent(const e: IAsn1Encodable): IAsn1Encodable;
 
     function ToString(): String;

+ 6 - 3
CryptoLib/src/Interfaces/ClpIDigest.pas

@@ -81,15 +81,18 @@ type
     /// <param name="outOff">
     /// the offset into the out array the digest is to start at.
     /// </param>
-    function DoFinal(const output: TCryptoLibByteArray; outOff: Int32)
-      : Int32; overload;
-    function DoFinal: TCryptoLibByteArray; overload;
+    function DoFinal(const output: TCryptoLibByteArray; outOff: Int32): Int32;
 
     /// <summary>
     /// Resets the digest back to it's initial state.
     /// </summary>
     procedure Reset();
 
+    /// <summary>
+    /// Clone the digest instance
+    /// </summary>
+    function Clone(): IDigest;
+
   end;
 
 implementation

+ 1 - 1
CryptoLib/src/Interfaces/ClpIECC.pas

@@ -23,7 +23,7 @@ interface
 
 uses
   Generics.Collections,
-  ClpIPreCompCallback,
+  ClpIPreCompCallBack,
   ClpCryptoLibTypes,
   ClpIFiniteField,
   ClpIPreCompInfo,

+ 36 - 0
CryptoLib/src/Interfaces/ClpIKdf1BytesGenerator.pas

@@ -0,0 +1,36 @@
+{ *********************************************************************************** }
+{ *                              CryptoLib Library                                  * }
+{ *                Copyright (c) 2018 - 20XX Ugochukwu Mmaduekwe                    * }
+{ *                 Github Repository <https://github.com/Xor-el>                   * }
+
+{ *  Distributed under the MIT software license, see the accompanying file LICENSE  * }
+{ *          or visit http://www.opensource.org/licenses/mit-license.php.           * }
+
+{ *                              Acknowledgements:                                  * }
+{ *                                                                                 * }
+{ *      Thanks to Sphere 10 Software (http://www.sphere10.com/) for sponsoring     * }
+{ *                           development of this library                           * }
+
+{ * ******************************************************************************* * }
+
+(* &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&& *)
+
+unit ClpIKdf1BytesGenerator;
+
+{$I ..\Include\CryptoLib.inc}
+
+interface
+
+uses
+  ClpIBaseKdfBytesGenerator;
+
+type
+
+  IKdf1BytesGenerator = interface(IBaseKdfBytesGenerator)
+    ['{FD2AF455-8C5D-4860-A1D5-B70E5D417841}']
+
+  end;
+
+implementation
+
+end.

+ 1 - 0
CryptoLib/src/Interfaces/ClpIKeyParameter.pas

@@ -31,6 +31,7 @@ type
     ['{92E7D4F7-40E5-4DC1-8058-23BE60848CC3}']
 
     function GetKey(): TCryptoLibByteArray;
+    procedure Clear();
 
   end;
 

+ 2 - 0
CryptoLib/src/Interfaces/ClpIMac.pas

@@ -35,6 +35,8 @@ type
   IMac = interface(IInterface)
     ['{3273EF2F-AE51-4878-B55C-5F801DB85A74}']
 
+    procedure Clear();
+
     /// <summary>
     /// returns the name of the algorithm the MAC implements.
     /// </summary>

+ 1 - 0
CryptoLib/src/Interfaces/ClpIParametersWithIV.pas

@@ -32,6 +32,7 @@ type
     function GetIV(): TCryptoLibByteArray;
     function GetParameters: ICipherParameters;
     property Parameters: ICipherParameters read GetParameters;
+    procedure Clear();
 
   end;
 

+ 1 - 32
CryptoLib/src/Interfaces/ClpIPbeParametersGenerator.pas

@@ -30,38 +30,7 @@ type
 
     ['{8C530FB2-6B8F-4E22-8EA0-D538665471EF}']
 
-    procedure Init(const password, salt: TCryptoLibByteArray;
-      iterationCount: Int32);
-
-    /// <returns>
-    /// the password byte array.
-    /// </returns>
-    function GetPassword: TCryptoLibByteArray;
-
-    /// <value>
-    /// the password byte array.
-    /// </value>
-    property password: TCryptoLibByteArray read GetPassword;
-
-    /// <returns>
-    /// the salt byte array.
-    /// </returns>
-    function GetSalt: TCryptoLibByteArray;
-
-    /// <value>
-    /// the salt byte array.
-    /// </value>
-    property salt: TCryptoLibByteArray read GetSalt;
-
-    /// <returns>
-    /// the iteration count.
-    /// </returns>
-    function GetIterationCount: Int32;
-
-    /// <value>
-    /// the iteration count.
-    /// </value>
-    property iterationCount: Int32 read GetIterationCount;
+    procedure Clear();
 
     /// <summary>
     /// Generate derived parameters for a key of length keySize.

+ 5 - 1
CryptoLib/src/Interfaces/ClpIPkcs5S2ParametersGenerator.pas

@@ -23,13 +23,17 @@ interface
 
 uses
   ClpIPbeParametersGenerator,
-  ClpIDigest;
+  ClpIDigest,
+  ClpCryptoLibTypes;
 
 type
   IPkcs5S2ParametersGenerator = interface(IPbeParametersGenerator)
 
     ['{AD345DB8-2341-4C56-B401-23444C2A81BA}']
 
+    procedure Init(const password, salt: TCryptoLibByteArray;
+      iterationCount: Int32);
+
     function GetDigest: IDigest;
 
     /// <value>

+ 40 - 0
CryptoLib/src/Interfaces/ClpIScryptParametersGenerator.pas

@@ -0,0 +1,40 @@
+{ *********************************************************************************** }
+{ *                              CryptoLib Library                                  * }
+{ *                Copyright (c) 2018 - 20XX Ugochukwu Mmaduekwe                    * }
+{ *                 Github Repository <https://github.com/Xor-el>                   * }
+
+{ *  Distributed under the MIT software license, see the accompanying file LICENSE  * }
+{ *          or visit http://www.opensource.org/licenses/mit-license.php.           * }
+
+{ *                              Acknowledgements:                                  * }
+{ *                                                                                 * }
+{ *      Thanks to Sphere 10 Software (http://www.sphere10.com/) for sponsoring     * }
+{ *                           development of this library                           * }
+
+{ * ******************************************************************************* * }
+
+(* &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&& *)
+
+unit ClpIScryptParametersGenerator;
+
+{$I ..\Include\CryptoLib.inc}
+
+interface
+
+uses
+  ClpIPbeParametersGenerator,
+  ClpCryptoLibTypes;
+
+type
+  IScryptParametersGenerator = interface(IPbeParametersGenerator)
+
+    ['{1EB9E081-1F90-409F-A5B9-3A999EB6CC70}']
+
+    procedure Init(const password, salt: TCryptoLibByteArray;
+      cost, blockSize, parallelism: Int32);
+
+  end;
+
+implementation
+
+end.

+ 20 - 1
CryptoLib/src/Math/ClpBigInteger.pas

@@ -424,6 +424,7 @@ type
     function SetBit(n: Int32): TBigInteger;
     function ClearBit(n: Int32): TBigInteger;
     function FlipBit(n: Int32): TBigInteger;
+    function IsEven(): Boolean; inline;
 
     function GetLowestSetBit(): Int32;
 
@@ -434,6 +435,8 @@ type
     function GetHashCode(): {$IFDEF DELPHI}Int32; {$ELSE}PtrInt;
     inline;
 {$ENDIF DELPHI}
+    function Clone(): TBigInteger; inline;
+
     class function BitCnt(i: Int32): Int32; static;
 
     /// <summary>
@@ -1958,6 +1961,11 @@ begin
   Result := &Xor(One.ShiftLeft(n));
 end;
 
+function TBigInteger.IsEven(): Boolean;
+begin
+  Result := not(TestBit(0));
+end;
+
 function TBigInteger.Gcd(const value: TBigInteger): TBigInteger;
 var
   r, u, v: TBigInteger;
@@ -2040,6 +2048,17 @@ begin
 
 end;
 
+function TBigInteger.Clone(): TBigInteger;
+begin
+  Result := Default (TBigInteger);
+  Result.Fmagnitude := System.Copy(Fmagnitude);
+  Result.Fsign := Fsign;
+  Result.FnBits := FnBits;
+  Result.FnBitLength := FnBitLength;
+  Result.FmQuote := FmQuote;
+  Result.FIsInitialized := FIsInitialized;
+end;
+
 function TBigInteger.GetLowestSetBit: Int32;
 begin
   if (Fsign = 0) then
@@ -2132,7 +2151,7 @@ end;
 
 function TBigInteger.IsEqualMagnitude(const x: TBigInteger): Boolean;
 var
-  i: Integer;
+  i: Int32;
   xMag: TCryptoLibInt32Array;
 begin
   xMag := x.Fmagnitude;

+ 0 - 95
CryptoLib/src/Math/EC/ClpValidityPrecompInfo.pas

@@ -1,95 +0,0 @@
-{ *********************************************************************************** }
-{ *                              CryptoLib Library                                  * }
-{ *                Copyright (c) 2018 - 20XX Ugochukwu Mmaduekwe                    * }
-{ *                 Github Repository <https://github.com/Xor-el>                   * }
-
-{ *  Distributed under the MIT software license, see the accompanying file LICENSE  * }
-{ *          or visit http://www.opensource.org/licenses/mit-license.php.           * }
-
-{ *                              Acknowledgements:                                  * }
-{ *                                                                                 * }
-{ *      Thanks to Sphere 10 Software (http://www.sphere10.com/) for sponsoring     * }
-{ *                           development of this library                           * }
-
-{ * ******************************************************************************* * }
-
-(* &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&& *)
-
-unit ClpValidityPrecompInfo;
-
-{$I ..\..\Include\CryptoLib.inc}
-
-interface
-
-uses
-  ClpIPreCompInfo,
-  ClpIValidityPrecompInfo;
-
-type
-  TValidityPrecompInfo = class(TInterfacedObject, IPreCompInfo,
-    IValidityPrecompInfo)
-
-  strict private
-
-  var
-    Ffailed, FcurveEquationPassed, ForderPassed: Boolean;
-
-  public
-
-    const
-    PRECOMP_NAME = 'bc_validity';
-
-    function HasFailed(): Boolean; inline;
-    procedure ReportFailed(); inline;
-    function HasCurveEquationPassed(): Boolean; inline;
-    procedure ReportCurveEquationPassed(); inline;
-    function HasOrderPassed(): Boolean; inline;
-    procedure ReportOrderPassed(); inline;
-
-    constructor Create();
-
-  end;
-
-implementation
-
-{ TValidityPrecompInfo }
-
-constructor TValidityPrecompInfo.Create;
-begin
-  Inherited Create();
-  Ffailed := False;
-  FcurveEquationPassed := False;
-  ForderPassed := False;
-end;
-
-function TValidityPrecompInfo.HasCurveEquationPassed: Boolean;
-begin
-  result := FcurveEquationPassed;
-end;
-
-function TValidityPrecompInfo.HasFailed: Boolean;
-begin
-  result := Ffailed;
-end;
-
-function TValidityPrecompInfo.HasOrderPassed: Boolean;
-begin
-  result := ForderPassed;
-end;
-
-procedure TValidityPrecompInfo.ReportCurveEquationPassed;
-begin
-  FcurveEquationPassed := True;
-end;
-
-procedure TValidityPrecompInfo.ReportFailed;
-begin
-  Ffailed := True;
-end;
-
-procedure TValidityPrecompInfo.ReportOrderPassed;
-begin
-  ForderPassed := True;
-end;
-
-end.

+ 19 - 0
CryptoLib/src/Math/EC/Rfc7748/ClpX25519.pas

@@ -1,5 +1,24 @@
+{ *********************************************************************************** }
+{ *                              CryptoLib Library                                  * }
+{ *                Copyright (c) 2018 - 20XX Ugochukwu Mmaduekwe                    * }
+{ *                 Github Repository <https://github.com/Xor-el>                   * }
+
+{ *  Distributed under the MIT software license, see the accompanying file LICENSE  * }
+{ *          or visit http://www.opensource.org/licenses/mit-license.php.           * }
+
+{ *                              Acknowledgements:                                  * }
+{ *                                                                                 * }
+{ *      Thanks to Sphere 10 Software (http://www.sphere10.com/) for sponsoring     * }
+{ *                           development of this library                           * }
+
+{ * ******************************************************************************* * }
+
+(* &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&& *)
+
 unit ClpX25519;
 
+{$I ..\..\..\Include\CryptoLib.inc}
+
 interface
 
 uses

+ 378 - 0
CryptoLib/src/Packages/Delphi/CryptoLib4PascalPackage.dpk

@@ -0,0 +1,378 @@
+package CryptoLib4PascalPackage;
+
+{$R *.res}
+{$WARNINGS OFF}
+{$HINTS OFF}
+{$IFDEF IMPLICITBUILDING This IFDEF should not be used by users}
+{$ALIGN 8}
+{$ASSERTIONS ON}
+{$BOOLEVAL OFF}
+{$DEBUGINFO OFF}
+{$EXTENDEDSYNTAX ON}
+{$IMPORTEDDATA ON}
+{$IOCHECKS ON}
+{$LOCALSYMBOLS OFF}
+{$LONGSTRINGS ON}
+{$OPENSTRINGS ON}
+{$OPTIMIZATION ON}
+{$OVERFLOWCHECKS OFF}
+{$RANGECHECKS OFF}
+{$REFERENCEINFO OFF}
+{$SAFEDIVIDE OFF}
+{$STACKFRAMES OFF}
+{$TYPEDADDRESS OFF}
+{$VARSTRINGCHECKS ON}
+{$WRITEABLECONST OFF}
+{$MINENUMSIZE 1}
+{$IMAGEBASE $400000}
+{$DEFINE RELEASE}
+{$ENDIF IMPLICITBUILDING}
+{$RUNONLY}
+{$IMPLICITBUILD ON}
+
+requires
+  rtl,
+  HashLib4PascalPackage,
+  SimpleBaseLib4PascalPackage;
+
+contains
+  ClpConverters in '..\..\Utils\ClpConverters.pas',
+  ClpOSRandom in '..\..\Utils\Randoms\ClpOSRandom.pas',
+  ClpRandomNumberGenerator in '..\..\Utils\Rng\ClpRandomNumberGenerator.pas',
+  ClpCryptoLibTypes in '..\..\Utils\ClpCryptoLibTypes.pas',
+  ClpBits in '..\..\Utils\ClpBits.pas',
+  ClpGeneratorUtilities in '..\..\Security\ClpGeneratorUtilities.pas',
+  ClpParameterUtilities in '..\..\Security\ClpParameterUtilities.pas',
+  ClpBitConverter in '..\..\Utils\ClpBitConverter.pas',
+  ClpCipherUtilities in '..\..\Security\ClpCipherUtilities.pas',
+  ClpNat in '..\..\Math\Raw\ClpNat.pas',
+  ClpX25519Field in '..\..\Math\EC\Rfc7748\ClpX25519Field.pas',
+  ClpEd25519 in '..\..\Math\EC\Rfc8032\ClpEd25519.pas',
+  ClpEd25519Blake2B in '..\..\Math\EC\Rfc8032\ClpEd25519Blake2B.pas',
+  ClpX25519 in '..\..\Math\EC\Rfc7748\ClpX25519.pas',
+  ClpBigInteger in '..\..\Math\ClpBigInteger.pas',
+  ClpCurve25519Custom in '..\..\Math\EC\Custom\Djb\ClpCurve25519Custom.pas',
+  ClpLongArray in '..\..\Math\EC\ClpLongArray.pas',
+  ClpECC in '..\..\Math\EC\ClpECC.pas',
+  ClpIX25519PublicKeyParameters in '..\..\Interfaces\ClpIX25519PublicKeyParameters.pas',
+  ClpIXSalsa20Engine in '..\..\Interfaces\ClpIXSalsa20Engine.pas',
+  ClpIX25519PrivateKeyParameters in '..\..\Interfaces\ClpIX25519PrivateKeyParameters.pas',
+  ClpIX25519KeyGenerationParameters in '..\..\Interfaces\ClpIX25519KeyGenerationParameters.pas',
+  ClpIX25519KeyPairGenerator in '..\..\Interfaces\ClpIX25519KeyPairGenerator.pas',
+  ClpIX25519Agreement in '..\..\Interfaces\ClpIX25519Agreement.pas',
+  ClpIStreamCipher in '..\..\Interfaces\ClpIStreamCipher.pas',
+  ClpISpeckLegacyEngine in '..\..\Interfaces\ClpISpeckLegacyEngine.pas',
+  ClpISpeckEngine in '..\..\Interfaces\ClpISpeckEngine.pas',
+  ClpIRawAgreement in '..\..\Interfaces\ClpIRawAgreement.pas',
+  ClpISignersEncodings in '..\..\Interfaces\ClpISignersEncodings.pas',
+  ClpIRijndaelEngine in '..\..\Interfaces\ClpIRijndaelEngine.pas',
+  ClpISalsa20Engine in '..\..\Interfaces\ClpISalsa20Engine.pas',
+  ClpIIESParameterSpec in '..\..\Interfaces\ClpIIESParameterSpec.pas',
+  ClpIIESWithCipherParameters in '..\..\Interfaces\ClpIIESWithCipherParameters.pas',
+  ClpIIESCipher in '..\..\Interfaces\ClpIIESCipher.pas',
+  ClpIEd25519PublicKeyParameters in '..\..\Interfaces\ClpIEd25519PublicKeyParameters.pas',
+  ClpIEd25519Signer in '..\..\Interfaces\ClpIEd25519Signer.pas',
+  ClpIEd25519PrivateKeyParameters in '..\..\Interfaces\ClpIEd25519PrivateKeyParameters.pas',
+  ClpIEd25519PhSigner in '..\..\Interfaces\ClpIEd25519PhSigner.pas',
+  ClpIEd25519KeyGenerationParameters in '..\..\Interfaces\ClpIEd25519KeyGenerationParameters.pas',
+  ClpIEd25519KeyPairGenerator in '..\..\Interfaces\ClpIEd25519KeyPairGenerator.pas',
+  ClpIEd25519PhBlake2BSigner in '..\..\Interfaces\ClpIEd25519PhBlake2BSigner.pas',
+  ClpIEd25519Blake2BPublicKeyParameters in '..\..\Interfaces\ClpIEd25519Blake2BPublicKeyParameters.pas',
+  ClpIEd25519CtxSigner in '..\..\Interfaces\ClpIEd25519CtxSigner.pas',
+  ClpIEd25519Blake2BSigner in '..\..\Interfaces\ClpIEd25519Blake2BSigner.pas',
+  ClpIEd25519CtxBlake2BSigner in '..\..\Interfaces\ClpIEd25519CtxBlake2BSigner.pas',
+  ClpIECPublicKeyParameters in '..\..\Interfaces\ClpIECPublicKeyParameters.pas',
+  ClpIEd25519Blake2BKeyGenerationParameters in '..\..\Interfaces\ClpIEd25519Blake2BKeyGenerationParameters.pas',
+  ClpIEd25519Blake2BKeyPairGenerator in '..\..\Interfaces\ClpIEd25519Blake2BKeyPairGenerator.pas',
+  ClpIEd25519Blake2BPrivateKeyParameters in '..\..\Interfaces\ClpIEd25519Blake2BPrivateKeyParameters.pas',
+  ClpIEd25519Blake2B in '..\..\Interfaces\ClpIEd25519Blake2B.pas',
+  ClpIECKeyParameters in '..\..\Interfaces\ClpIECKeyParameters.pas',
+  ClpIEd25519 in '..\..\Interfaces\ClpIEd25519.pas',
+  ClpIDsaPublicKeyParameters in '..\..\Interfaces\ClpIDsaPublicKeyParameters.pas',
+  ClpIDsaPrivateKeyParameters in '..\..\Interfaces\ClpIDsaPrivateKeyParameters.pas',
+  ClpIECPrivateKeyParameters in '..\..\Interfaces\ClpIECPrivateKeyParameters.pas',
+  ClpIDsaKeyParameters in '..\..\Interfaces\ClpIDsaKeyParameters.pas',
+  ClpIBufferedStreamCipher in '..\..\Interfaces\ClpIBufferedStreamCipher.pas',
+  ClpICurve25519Custom in '..\..\Interfaces\ClpICurve25519Custom.pas',
+  ClpIChaChaEngine in '..\..\Interfaces\ClpIChaChaEngine.pas',
+  ClpIBlockCipherModes in '..\..\Interfaces\ClpIBlockCipherModes.pas',
+  ClpIAlgorithmParameterSpec in '..\..\Interfaces\ClpIAlgorithmParameterSpec.pas',
+  ClpSchnorrDigestSigner in '..\..\Crypto\Signers\ClpSchnorrDigestSigner.pas',
+  ClpEd25519Signer in '..\..\Crypto\Signers\ClpEd25519Signer.pas',
+  ClpEd25519PhBlake2BSigner in '..\..\Crypto\Signers\ClpEd25519PhBlake2BSigner.pas',
+  ClpEd25519PhSigner in '..\..\Crypto\Signers\ClpEd25519PhSigner.pas',
+  ClpEd25519CtxSigner in '..\..\Crypto\Signers\ClpEd25519CtxSigner.pas',
+  ClpEd25519CtxBlake2BSigner in '..\..\Crypto\Signers\ClpEd25519CtxBlake2BSigner.pas',
+  ClpX25519KeyGenerationParameters in '..\..\Crypto\Parameters\ClpX25519KeyGenerationParameters.pas',
+  ClpEd25519Blake2BSigner in '..\..\Crypto\Signers\ClpEd25519Blake2BSigner.pas',
+  ClpX25519PublicKeyParameters in '..\..\Crypto\Parameters\ClpX25519PublicKeyParameters.pas',
+  ClpX25519PrivateKeyParameters in '..\..\Crypto\Parameters\ClpX25519PrivateKeyParameters.pas',
+  ClpIESWithCipherParameters in '..\..\Crypto\Parameters\ClpIESWithCipherParameters.pas',
+  ClpIESParameters in '..\..\Crypto\Parameters\ClpIESParameters.pas',
+  ClpIESParameterSpec in '..\..\Crypto\Parameters\ClpIESParameterSpec.pas',
+  ClpEd25519Blake2BPublicKeyParameters in '..\..\Crypto\Parameters\ClpEd25519Blake2BPublicKeyParameters.pas',
+  ClpEd25519PrivateKeyParameters in '..\..\Crypto\Parameters\ClpEd25519PrivateKeyParameters.pas',
+  ClpEd25519PublicKeyParameters in '..\..\Crypto\Parameters\ClpEd25519PublicKeyParameters.pas',
+  ClpEd25519KeyGenerationParameters in '..\..\Crypto\Parameters\ClpEd25519KeyGenerationParameters.pas',
+  ClpEd25519Blake2BKeyGenerationParameters in '..\..\Crypto\Parameters\ClpEd25519Blake2BKeyGenerationParameters.pas',
+  ClpEd25519Blake2BPrivateKeyParameters in '..\..\Crypto\Parameters\ClpEd25519Blake2BPrivateKeyParameters.pas',
+  ClpECPublicKeyParameters in '..\..\Crypto\Parameters\ClpECPublicKeyParameters.pas',
+  ClpBlockCipherModes in '..\..\Crypto\Modes\ClpBlockCipherModes.pas',
+  ClpECKeyParameters in '..\..\Crypto\Parameters\ClpECKeyParameters.pas',
+  ClpECPrivateKeyParameters in '..\..\Crypto\Parameters\ClpECPrivateKeyParameters.pas',
+  ClpDsaPrivateKeyParameters in '..\..\Crypto\Parameters\ClpDsaPrivateKeyParameters.pas',
+  ClpDsaPublicKeyParameters in '..\..\Crypto\Parameters\ClpDsaPublicKeyParameters.pas',
+  ClpX25519KeyPairGenerator in '..\..\Crypto\Generators\ClpX25519KeyPairGenerator.pas',
+  ClpPascalCoinECIESKdfBytesGenerator in '..\..\Crypto\Generators\ClpPascalCoinECIESKdfBytesGenerator.pas',
+  ClpDsaKeyParameters in '..\..\Crypto\Parameters\ClpDsaKeyParameters.pas',
+  ClpSpeckLegacyEngine in '..\..\Crypto\Engines\ClpSpeckLegacyEngine.pas',
+  ClpEd25519Blake2BKeyPairGenerator in '..\..\Crypto\Generators\ClpEd25519Blake2BKeyPairGenerator.pas',
+  ClpEd25519KeyPairGenerator in '..\..\Crypto\Generators\ClpEd25519KeyPairGenerator.pas',
+  ClpXSalsa20Engine in '..\..\Crypto\Engines\ClpXSalsa20Engine.pas',
+  ClpSpeckEngine in '..\..\Crypto\Engines\ClpSpeckEngine.pas',
+  ClpBlowfishEngine in '..\..\Crypto\Engines\ClpBlowfishEngine.pas',
+  ClpIESEngine in '..\..\Crypto\Engines\ClpIESEngine.pas',
+  ClpSalsa20Engine in '..\..\Crypto\Engines\ClpSalsa20Engine.pas',
+  ClpRijndaelEngine in '..\..\Crypto\Engines\ClpRijndaelEngine.pas',
+  ClpPascalCoinIESEngine in '..\..\Crypto\Engines\ClpPascalCoinIESEngine.pas',
+  ClpAesLightEngine in '..\..\Crypto\Engines\ClpAesLightEngine.pas',
+  ClpCustomNamedCurves in '..\..\Crypto\EC\ClpCustomNamedCurves.pas',
+  ClpChaChaEngine in '..\..\Crypto\Engines\ClpChaChaEngine.pas',
+  ClpAesEngine in '..\..\Crypto\Engines\ClpAesEngine.pas',
+  ClpAsn1Objects in '..\..\Asn1\ClpAsn1Objects.pas',
+  ClpIESCipher in '..\..\Crypto\ClpIESCipher.pas',
+  ClpBufferedCipherBase in '..\..\Crypto\ClpBufferedCipherBase.pas',
+  ClpKeyGenerationParameters in '..\..\Crypto\ClpKeyGenerationParameters.pas',
+  ClpBufferedStreamCipher in '..\..\Crypto\ClpBufferedStreamCipher.pas',
+  ClpX25519Agreement in '..\..\Crypto\Agreement\ClpX25519Agreement.pas',
+  ClpAsymmetricKeyParameter in '..\..\Crypto\ClpAsymmetricKeyParameter.pas',
+  ClpX9ECParametersHolder in '..\..\Asn1\X9\ClpX9ECParametersHolder.pas',
+  ClpEdECObjectIdentifiers in '..\..\Asn1\Edec\ClpEdECObjectIdentifiers.pas',
+  ClpTnaf in '..\..\Math\EC\Abc\ClpTnaf.pas',
+  ClpECAlgorithms in '..\..\Math\EC\ClpECAlgorithms.pas',
+  ClpEphemeralKeyPair in '..\..\Crypto\ClpEphemeralKeyPair.pas',
+  ClpIKeyEncoder in '..\..\Interfaces\ClpIKeyEncoder.pas',
+  ClpSecureRandom in '..\..\Security\ClpSecureRandom.pas',
+  ClpSimpleBigDecimal in '..\..\Math\EC\Abc\ClpSimpleBigDecimal.pas',
+  ClpSignersEncodings in '..\..\Crypto\Signers\SignersEncodings\ClpSignersEncodings.pas',
+  ClpIECC in '..\..\Interfaces\ClpIECC.pas',
+  ClpSignerUtilities in '..\..\Security\ClpSignerUtilities.pas',
+  ClpECDsaSigner in '..\..\Crypto\Signers\ClpECDsaSigner.pas',
+  ClpSecT283Custom in '..\..\Math\EC\Custom\Sec\ClpSecT283Custom.pas',
+  ClpSecP521R1Custom in '..\..\Math\EC\Custom\Sec\ClpSecP521R1Custom.pas',
+  ClpSecP384R1Custom in '..\..\Math\EC\Custom\Sec\ClpSecP384R1Custom.pas',
+  ClpSecP256R1Custom in '..\..\Math\EC\Custom\Sec\ClpSecP256R1Custom.pas',
+  ClpSecP256K1Custom in '..\..\Math\EC\Custom\Sec\ClpSecP256K1Custom.pas',
+  ClpX9ECC in '..\..\Asn1\X9\ClpX9ECC.pas',
+  ClpDigestUtilities in '..\..\Security\ClpDigestUtilities.pas',
+  ClpECGost3410NamedCurves in '..\..\Asn1\CryptoPro\ClpECGost3410NamedCurves.pas',
+  ClpDigestRandomGenerator in '..\..\Crypto\Prng\ClpDigestRandomGenerator.pas',
+  ClpCryptoApiRandomGenerator in '..\..\Crypto\Prng\ClpCryptoApiRandomGenerator.pas',
+  ClpSecNamedCurves in '..\..\Asn1\Sec\ClpSecNamedCurves.pas',
+  ClpMod in '..\..\Math\Raw\ClpMod.pas',
+  ClpFiniteFields in '..\..\Math\Field\ClpFiniteFields.pas',
+  ClpECDomainParameters in '..\..\Crypto\Parameters\ClpECDomainParameters.pas',
+  ClpRandom in '..\..\Security\ClpRandom.pas',
+  ClpDsaDigestSigner in '..\..\Crypto\Signers\ClpDsaDigestSigner.pas',
+  ClpEncoders in '..\..\Utils\Encoders\ClpEncoders.pas',
+  ClpDsaParametersGenerator in '..\..\Crypto\Generators\ClpDsaParametersGenerator.pas',
+  ClpNistNamedCurves in '..\..\Asn1\Nist\ClpNistNamedCurves.pas',
+  ClpMacUtilities in '..\..\Security\ClpMacUtilities.pas',
+  ClpDsaKeyPairGenerator in '..\..\Crypto\Generators\ClpDsaKeyPairGenerator.pas',
+  ClpIEphemeralKeyPair in '..\..\Interfaces\ClpIEphemeralKeyPair.pas',
+  ClpCryptoProObjectIdentifiers in '..\..\Asn1\CryptoPro\ClpCryptoProObjectIdentifiers.pas',
+  ClpDsaParameter in '..\..\Asn1\X509\ClpDsaParameter.pas',
+  ClpEacObjectIdentifiers in '..\..\Asn1\Eac\ClpEacObjectIdentifiers.pas',
+  ClpECKeyGenerationParameters in '..\..\Crypto\Parameters\ClpECKeyGenerationParameters.pas',
+  ClpECKeyPairGenerator in '..\..\Crypto\Generators\ClpECKeyPairGenerator.pas',
+  ClpECNamedCurveTable in '..\..\Asn1\X9\ClpECNamedCurveTable.pas',
+  ClpIanaObjectIdentifiers in '..\..\Asn1\Iana\ClpIanaObjectIdentifiers.pas',
+  ClpIDsaParameter in '..\..\Interfaces\ClpIDsaParameter.pas',
+  ClpIECKeyGenerationParameters in '..\..\Interfaces\ClpIECKeyGenerationParameters.pas',
+  ClpIX9ECC in '..\..\Interfaces\ClpIX9ECC.pas',
+  ClpIX9ECParameters in '..\..\Interfaces\ClpIX9ECParameters.pas',
+  ClpMiscObjectIdentifiers in '..\..\Asn1\Misc\ClpMiscObjectIdentifiers.pas',
+  ClpNistObjectIdentifiers in '..\..\Asn1\Nist\ClpNistObjectIdentifiers.pas',
+  ClpOiwObjectIdentifiers in '..\..\Asn1\Oiw\ClpOiwObjectIdentifiers.pas',
+  ClpPkcsObjectIdentifiers in '..\..\Asn1\Pkcs\ClpPkcsObjectIdentifiers.pas',
+  ClpRosstandartObjectIdentifiers in '..\..\Asn1\RossStandart\ClpRosstandartObjectIdentifiers.pas',
+  ClpSecObjectIdentifiers in '..\..\Asn1\Sec\ClpSecObjectIdentifiers.pas',
+  ClpTeleTrusTObjectIdentifiers in '..\..\Asn1\TeleTrust\ClpTeleTrusTObjectIdentifiers.pas',
+  ClpX9ECParameters in '..\..\Asn1\X9\ClpX9ECParameters.pas',
+  ClpX9ObjectIdentifiers in '..\..\Asn1\X9\ClpX9ObjectIdentifiers.pas',
+  ClpBsiObjectIdentifiers in '..\..\Asn1\Bsi\ClpBsiObjectIdentifiers.pas',
+  ClpIAsn1Objects in '..\..\Interfaces\ClpIAsn1Objects.pas',
+  ClpECIESPublicKeyParser in '..\..\Crypto\Parsers\ClpECIESPublicKeyParser.pas',
+  ClpECCurveConstants in '..\..\Math\EC\ClpECCurveConstants.pas',
+  ClpECSchnorrSipaSigner in '..\..\Crypto\Signers\ClpECSchnorrSipaSigner.pas',
+  ClpIBlowfishEngine in '..\..\Interfaces\ClpIBlowfishEngine.pas',
+  ClpIDsaExt in '..\..\Interfaces\ClpIDsaExt.pas',
+  ClpIECSchnorrSipaSigner in '..\..\Interfaces\ClpIECSchnorrSipaSigner.pas',
+  ClpIPaddingModes in '..\..\Interfaces\ClpIPaddingModes.pas',
+  ClpISchnorr in '..\..\Interfaces\ClpISchnorr.pas',
+  ClpISchnorrDigestSigner in '..\..\Interfaces\ClpISchnorrDigestSigner.pas',
+  ClpISchnorrExt in '..\..\Interfaces\ClpISchnorrExt.pas',
+  ClpISecP256K1Custom in '..\..\Interfaces\ClpISecP256K1Custom.pas',
+  ClpISecP256R1Custom in '..\..\Interfaces\ClpISecP256R1Custom.pas',
+  ClpISecP384R1Custom in '..\..\Interfaces\ClpISecP384R1Custom.pas',
+  ClpISecP521R1Custom in '..\..\Interfaces\ClpISecP521R1Custom.pas',
+  ClpISecT283Custom in '..\..\Interfaces\ClpISecT283Custom.pas',
+  ClpPaddingModes in '..\..\Crypto\Paddings\ClpPaddingModes.pas',
+  ClpDigest in '..\..\Crypto\Digests\ClpDigest.pas',
+  ClpDsaParameterGenerationParameters in '..\..\Crypto\Parameters\ClpDsaParameterGenerationParameters.pas',
+  ClpDsaSigner in '..\..\Crypto\Signers\ClpDsaSigner.pas',
+  ClpECDHCBasicAgreement in '..\..\Crypto\Agreement\ClpECDHCBasicAgreement.pas',
+  ClpHkdfBytesGenerator in '..\..\Crypto\Generators\ClpHkdfBytesGenerator.pas',
+  ClpHkdfParameters in '..\..\Crypto\Parameters\ClpHkdfParameters.pas',
+  ClpHMacDsaKCalculator in '..\..\Crypto\Signers\ClpHMacDsaKCalculator.pas',
+  ClpIAesLightEngine in '..\..\Interfaces\ClpIAesLightEngine.pas',
+  ClpIDsaKeyPairGenerator in '..\..\Interfaces\ClpIDsaKeyPairGenerator.pas',
+  ClpIDsaParameterGenerationParameters in '..\..\Interfaces\ClpIDsaParameterGenerationParameters.pas',
+  ClpIDsaParametersGenerator in '..\..\Interfaces\ClpIDsaParametersGenerator.pas',
+  ClpIDsaSigner in '..\..\Interfaces\ClpIDsaSigner.pas',
+  ClpIECDHCBasicAgreement in '..\..\Interfaces\ClpIECDHCBasicAgreement.pas',
+  ClpIHkdfBytesGenerator in '..\..\Interfaces\ClpIHkdfBytesGenerator.pas',
+  ClpIHkdfParameters in '..\..\Interfaces\ClpIHkdfParameters.pas',
+  ClpIHMacDsaKCalculator in '..\..\Interfaces\ClpIHMacDsaKCalculator.pas',
+  ClpInterleave in '..\..\Math\Raw\ClpInterleave.pas',
+  ClpIPreCompCallBack in '..\..\Interfaces\ClpIPreCompCallBack.pas',
+  ClpIValidityPrecompInfo in '..\..\Interfaces\ClpIValidityPrecompInfo.pas',
+  ClpNat192 in '..\..\Math\Raw\ClpNat192.pas',
+  ClpNat256 in '..\..\Math\Raw\ClpNat256.pas',
+  ClpNat320 in '..\..\Math\Raw\ClpNat320.pas',
+  ClpNat384 in '..\..\Math\Raw\ClpNat384.pas',
+  ClpNat512 in '..\..\Math\Raw\ClpNat512.pas',
+  ClpBaseKdfBytesGenerator in '..\..\Crypto\Generators\ClpBaseKdfBytesGenerator.pas',
+  ClpCipherKeyGenerator in '..\..\Crypto\Generators\ClpCipherKeyGenerator.pas',
+  ClpDsaKeyGenerationParameters in '..\..\Crypto\Parameters\ClpDsaKeyGenerationParameters.pas',
+  ClpDsaParameters in '..\..\Crypto\Parameters\ClpDsaParameters.pas',
+  ClpDsaValidationParameters in '..\..\Crypto\Parameters\ClpDsaValidationParameters.pas',
+  ClpECNRSigner in '..\..\Crypto\Signers\ClpECNRSigner.pas',
+  ClpEphemeralKeyPairGenerator in '..\..\Crypto\Generators\ClpEphemeralKeyPairGenerator.pas',
+  ClpHMac in '..\..\Crypto\Macs\ClpHMac.pas',
+  ClpIBaseKdfBytesGenerator in '..\..\Interfaces\ClpIBaseKdfBytesGenerator.pas',
+  ClpIBasicAgreement in '..\..\Interfaces\ClpIBasicAgreement.pas',
+  ClpICipherKeyGenerator in '..\..\Interfaces\ClpICipherKeyGenerator.pas',
+  ClpIDerivationFunction in '..\..\Interfaces\ClpIDerivationFunction.pas',
+  ClpIDerivationParameters in '..\..\Interfaces\ClpIDerivationParameters.pas',
+  ClpIDigest in '..\..\Interfaces\ClpIDigest.pas',
+  ClpIDsaKeyGenerationParameters in '..\..\Interfaces\ClpIDsaKeyGenerationParameters.pas',
+  ClpIDsaParameters in '..\..\Interfaces\ClpIDsaParameters.pas',
+  ClpIDsaValidationParameters in '..\..\Interfaces\ClpIDsaValidationParameters.pas',
+  ClpIECDHBasicAgreement in '..\..\Interfaces\ClpIECDHBasicAgreement.pas',
+  ClpIECIESPublicKeyParser in '..\..\Interfaces\ClpIECIESPublicKeyParser.pas',
+  ClpIECNRSigner in '..\..\Interfaces\ClpIECNRSigner.pas',
+  ClpIEphemeralKeyPairGenerator in '..\..\Interfaces\ClpIEphemeralKeyPairGenerator.pas',
+  ClpIHMac in '..\..\Interfaces\ClpIHMac.pas',
+  ClpIIESEngine in '..\..\Interfaces\ClpIIESEngine.pas',
+  ClpIIESParameters in '..\..\Interfaces\ClpIIESParameters.pas',
+  ClpIIso18033KdfParameters in '..\..\Interfaces\ClpIIso18033KdfParameters.pas',
+  ClpIKdf2BytesGenerator in '..\..\Interfaces\ClpIKdf2BytesGenerator.pas',
+  ClpIKdfParameters in '..\..\Interfaces\ClpIKdfParameters.pas',
+  ClpIKeyParser in '..\..\Interfaces\ClpIKeyParser.pas',
+  ClpIMac in '..\..\Interfaces\ClpIMac.pas',
+  ClpIPascalCoinECIESKdfBytesGenerator in '..\..\Interfaces\ClpIPascalCoinECIESKdfBytesGenerator.pas',
+  ClpIPascalCoinIESEngine in '..\..\Interfaces\ClpIPascalCoinIESEngine.pas',
+  ClpIPbeParametersGenerator in '..\..\Interfaces\ClpIPbeParametersGenerator.pas',
+  ClpIPkcs5S2ParametersGenerator in '..\..\Interfaces\ClpIPkcs5S2ParametersGenerator.pas',
+  ClpIso18033KdfParameters in '..\..\Crypto\Parameters\ClpIso18033KdfParameters.pas',
+  ClpKdf2BytesGenerator in '..\..\Crypto\Generators\ClpKdf2BytesGenerator.pas',
+  ClpKdfParameters in '..\..\Crypto\Parameters\ClpKdfParameters.pas',
+  ClpKeyEncoder in '..\..\Crypto\ClpKeyEncoder.pas',
+  ClpPbeParametersGenerator in '..\..\Crypto\Generators\ClpPbeParametersGenerator.pas',
+  ClpPkcs5S2ParametersGenerator in '..\..\Crypto\Generators\ClpPkcs5S2ParametersGenerator.pas',
+  ClpStringUtils in '..\..\Utils\ClpStringUtils.pas',
+  ClpBufferedBlockCipher in '..\..\Crypto\ClpBufferedBlockCipher.pas',
+  ClpCheck in '..\..\Utils\ClpCheck.pas',
+  ClpECDHBasicAgreement in '..\..\Crypto\Agreement\ClpECDHBasicAgreement.pas',
+  ClpGenericPolynomialExtensionField in '..\..\Math\Field\ClpGenericPolynomialExtensionField.pas',
+  ClpGF2Polynomial in '..\..\Math\Field\ClpGF2Polynomial.pas',
+  ClpGlvMultiplier in '..\..\Math\EC\Multiplier\ClpGlvMultiplier.pas',
+  ClpIAesEngine in '..\..\Interfaces\ClpIAesEngine.pas',
+  ClpIBlockCipher in '..\..\Interfaces\ClpIBlockCipher.pas',
+  ClpIBlockCipherPadding in '..\..\Interfaces\ClpIBlockCipherPadding.pas',
+  ClpIBufferedBlockCipher in '..\..\Interfaces\ClpIBufferedBlockCipher.pas',
+  ClpIBufferedCipher in '..\..\Interfaces\ClpIBufferedCipher.pas',
+  ClpIBufferedCipherBase in '..\..\Interfaces\ClpIBufferedCipherBase.pas',
+  ClpIDsaDigestSigner in '..\..\Interfaces\ClpIDsaDigestSigner.pas',
+  ClpIGenericPolynomialExtensionField in '..\..\Interfaces\ClpIGenericPolynomialExtensionField.pas',
+  ClpIGF2Polynomial in '..\..\Interfaces\ClpIGF2Polynomial.pas',
+  ClpIGlvMultiplier in '..\..\Interfaces\ClpIGlvMultiplier.pas',
+  ClpIKeyParameter in '..\..\Interfaces\ClpIKeyParameter.pas',
+  ClpIPaddedBufferedBlockCipher in '..\..\Interfaces\ClpIPaddedBufferedBlockCipher.pas',
+  ClpIParametersWithIV in '..\..\Interfaces\ClpIParametersWithIV.pas',
+  ClpIPrimeField in '..\..\Interfaces\ClpIPrimeField.pas',
+  ClpIWNafL2RMultiplier in '..\..\Interfaces\ClpIWNafL2RMultiplier.pas',
+  ClpIWTauNafMultiplier in '..\..\Interfaces\ClpIWTauNafMultiplier.pas',
+  ClpIWTauNafPreCompInfo in '..\..\Interfaces\ClpIWTauNafPreCompInfo.pas',
+  ClpIZTauElement in '..\..\Interfaces\ClpIZTauElement.pas',
+  ClpKeyParameter in '..\..\Crypto\Parameters\ClpKeyParameter.pas',
+  ClpPaddedBufferedBlockCipher in '..\..\Crypto\Paddings\ClpPaddedBufferedBlockCipher.pas',
+  ClpParametersWithIV in '..\..\Crypto\Parameters\ClpParametersWithIV.pas',
+  ClpPrimeField in '..\..\Math\Field\ClpPrimeField.pas',
+  ClpSetWeakRef in '..\..\Utils\ClpSetWeakRef.pas',
+  ClpWNafL2RMultiplier in '..\..\Math\EC\Multiplier\ClpWNafL2RMultiplier.pas',
+  ClpWTauNafMultiplier in '..\..\Math\EC\Multiplier\ClpWTauNafMultiplier.pas',
+  ClpWTauNafPreCompInfo in '..\..\Math\EC\Multiplier\ClpWTauNafPreCompInfo.pas',
+  ClpZTauElement in '..\..\Math\EC\Abc\ClpZTauElement.pas',
+  ClpAbstractECMultiplier in '..\..\Math\EC\Multiplier\ClpAbstractECMultiplier.pas',
+  ClpArrayUtils in '..\..\Utils\ClpArrayUtils.pas',
+  ClpBigIntegers in '..\..\Utils\ClpBigIntegers.pas',
+  ClpFixedPointCombMultiplier in '..\..\Math\EC\Multiplier\ClpFixedPointCombMultiplier.pas',
+  ClpFixedPointPreCompInfo in '..\..\Math\EC\Multiplier\ClpFixedPointPreCompInfo.pas',
+  ClpFixedPointUtilities in '..\..\Math\EC\Multiplier\ClpFixedPointUtilities.pas',
+  ClpGlvTypeBEndomorphism in '..\..\Math\EC\Endo\ClpGlvTypeBEndomorphism.pas',
+  ClpGlvTypeBParameters in '..\..\Math\EC\Endo\ClpGlvTypeBParameters.pas',
+  ClpIDsa in '..\..\Interfaces\ClpIDsa.pas',
+  ClpIDsaKCalculator in '..\..\Interfaces\ClpIDsaKCalculator.pas',
+  ClpIECDsaSigner in '..\..\Interfaces\ClpIECDsaSigner.pas',
+  ClpIFiniteField in '..\..\Interfaces\ClpIFiniteField.pas',
+  ClpIFixedPointCombMultiplier in '..\..\Interfaces\ClpIFixedPointCombMultiplier.pas',
+  ClpIFixedPointPreCompInfo in '..\..\Interfaces\ClpIFixedPointPreCompInfo.pas',
+  ClpIGlvEndomorphism in '..\..\Interfaces\ClpIGlvEndomorphism.pas',
+  ClpIGlvTypeBEndomorphism in '..\..\Interfaces\ClpIGlvTypeBEndomorphism.pas',
+  ClpIGlvTypeBParameters in '..\..\Interfaces\ClpIGlvTypeBParameters.pas',
+  ClpIKeyGenerationParameters in '..\..\Interfaces\ClpIKeyGenerationParameters.pas',
+  ClpIOidTokenizer in '..\..\Interfaces\ClpIOidTokenizer.pas',
+  ClpIParametersWithRandom in '..\..\Interfaces\ClpIParametersWithRandom.pas',
+  ClpIPolynomial in '..\..\Interfaces\ClpIPolynomial.pas',
+  ClpIPolynomialExtensionField in '..\..\Interfaces\ClpIPolynomialExtensionField.pas',
+  ClpIPreCompInfo in '..\..\Interfaces\ClpIPreCompInfo.pas',
+  ClpIRandom in '..\..\Interfaces\ClpIRandom.pas',
+  ClpIRandomDsaKCalculator in '..\..\Interfaces\ClpIRandomDsaKCalculator.pas',
+  ClpIRandomGenerator in '..\..\Interfaces\ClpIRandomGenerator.pas',
+  ClpIRandomNumberGenerator in '..\..\Interfaces\ClpIRandomNumberGenerator.pas',
+  ClpIScaleXPointMap in '..\..\Interfaces\ClpIScaleXPointMap.pas',
+  ClpISecureRandom in '..\..\Interfaces\ClpISecureRandom.pas',
+  ClpISigner in '..\..\Interfaces\ClpISigner.pas',
+  ClpIWNafPreCompInfo in '..\..\Interfaces\ClpIWNafPreCompInfo.pas',
+  ClpIX9ECParametersHolder in '..\..\Interfaces\ClpIX9ECParametersHolder.pas',
+  ClpParametersWithRandom in '..\..\Crypto\Parameters\ClpParametersWithRandom.pas',
+  ClpPcgRandomMinimal in '..\..\Utils\Randoms\ClpPcgRandomMinimal.pas',
+  ClpRandomDsaKCalculator in '..\..\Crypto\Signers\ClpRandomDsaKCalculator.pas',
+  ClpScaleXPointMap in '..\..\Math\EC\ClpScaleXPointMap.pas',
+  ClpTimes in '..\..\Utils\ClpTimes.pas',
+  ClpWNafPreCompInfo in '..\..\Math\EC\Multiplier\ClpWNafPreCompInfo.pas',
+  ClpAsymmetricCipherKeyPair in '..\..\Crypto\ClpAsymmetricCipherKeyPair.pas',
+  ClpIAbstractECMultiplier in '..\..\Interfaces\ClpIAbstractECMultiplier.pas',
+  ClpIAsymmetricCipherKeyPair in '..\..\Interfaces\ClpIAsymmetricCipherKeyPair.pas',
+  ClpIAsymmetricCipherKeyPairGenerator in '..\..\Interfaces\ClpIAsymmetricCipherKeyPairGenerator.pas',
+  ClpIAsymmetricKeyParameter in '..\..\Interfaces\ClpIAsymmetricKeyParameter.pas',
+  ClpICipherParameters in '..\..\Interfaces\ClpICipherParameters.pas',
+  ClpICryptoApiRandomGenerator in '..\..\Interfaces\ClpICryptoApiRandomGenerator.pas',
+  ClpIDigestRandomGenerator in '..\..\Interfaces\ClpIDigestRandomGenerator.pas',
+  ClpIECDomainParameters in '..\..\Interfaces\ClpIECDomainParameters.pas',
+  ClpIECKeyPairGenerator in '..\..\Interfaces\ClpIECKeyPairGenerator.pas',
+  ClpIExtensionField in '..\..\Interfaces\ClpIExtensionField.pas',
+  ClpOidTokenizer in '..\..\Asn1\ClpOidTokenizer.pas',
+  ClpValidityPrecompInfo in '..\..\Math\EC\Multiplier\ClpValidityPrecompInfo.pas',
+  ClpTeleTrusTNamedCurves in '..\..\Asn1\TeleTrust\ClpTeleTrusTNamedCurves.pas',
+  ClpAgreementUtilities in '..\..\Security\ClpAgreementUtilities.pas',
+  ClpIKdf1BytesGenerator in '..\..\Interfaces\ClpIKdf1BytesGenerator.pas',
+  ClpKdf1BytesGenerator in '..\..\Crypto\Generators\ClpKdf1BytesGenerator.pas',
+  ClpIArgon2ParametersGenerator in '..\..\Interfaces\ClpIArgon2ParametersGenerator.pas',
+  ClpArgon2ParametersGenerator in '..\..\Crypto\Generators\ClpArgon2ParametersGenerator.pas',
+  ClpIScryptParametersGenerator in '..\..\Interfaces\ClpIScryptParametersGenerator.pas',
+  ClpScryptParametersGenerator in '..\..\Crypto\Generators\ClpScryptParametersGenerator.pas';
+
+end.

+ 272 - 244
CryptoLib/src/Packages/FPC/CryptoLib4PascalPackage.lpk

@@ -25,7 +25,7 @@
  Acknowledgements: 
 Thanks to Sphere 10 Software (http://www.sphere10.com/) for sponsoring the development of this library "/>
     <Version Major="3" Minor="1"/>
-    <Files Count="334">
+    <Files Count="341">
       <Item1>
         <Filename Value="..\..\Asn1\ClpOidTokenizer.pas"/>
         <UnitName Value="ClpOidTokenizer"/>
@@ -888,482 +888,510 @@ Thanks to Sphere 10 Software (http://www.sphere10.com/) for sponsoring the devel
         <UnitName Value="ClpIDsaParameterGenerationParameters"/>
       </Item215>
       <Item216>
-        <Filename Value="..\..\Math\EC\ClpValidityPrecompInfo.pas"/>
-        <UnitName Value="ClpValidityPrecompInfo"/>
-      </Item216>
-      <Item217>
         <Filename Value="..\..\Interfaces\ClpIValidityPrecompInfo.pas"/>
         <UnitName Value="ClpIValidityPrecompInfo"/>
-      </Item217>
-      <Item218>
+      </Item216>
+      <Item217>
         <Filename Value="..\..\Crypto\Generators\ClpDsaParametersGenerator.pas"/>
         <UnitName Value="ClpDsaParametersGenerator"/>
-      </Item218>
-      <Item219>
+      </Item217>
+      <Item218>
         <Filename Value="..\..\Asn1\X509\ClpDsaParameter.pas"/>
         <UnitName Value="ClpDsaParameter"/>
-      </Item219>
-      <Item220>
+      </Item218>
+      <Item219>
         <Filename Value="..\..\Interfaces\ClpIDsaParameter.pas"/>
         <UnitName Value="ClpIDsaParameter"/>
-      </Item220>
-      <Item221>
+      </Item219>
+      <Item220>
         <Filename Value="..\..\Interfaces\ClpIKeyEncoder.pas"/>
         <UnitName Value="ClpIKeyEncoder"/>
-      </Item221>
-      <Item222>
+      </Item220>
+      <Item221>
         <Filename Value="..\..\Interfaces\ClpIDsaParametersGenerator.pas"/>
         <UnitName Value="ClpIDsaParametersGenerator"/>
-      </Item222>
-      <Item223>
+      </Item221>
+      <Item222>
         <Filename Value="..\..\Interfaces\ClpIPreCompCallBack.pas"/>
         <UnitName Value="ClpIPreCompCallBack"/>
-      </Item223>
-      <Item224>
+      </Item222>
+      <Item223>
         <Filename Value="..\..\Math\EC\Multiplier\ClpValidityPrecompInfo.pas"/>
         <AddToUsesPkgSection Value="False"/>
         <UnitName Value="ClpValidityPrecompInfo"/>
-      </Item224>
-      <Item225>
+      </Item223>
+      <Item224>
         <Filename Value="..\..\Asn1\Nist\ClpNistNamedCurves.pas"/>
         <UnitName Value="ClpNistNamedCurves"/>
-      </Item225>
-      <Item226>
+      </Item224>
+      <Item225>
         <Filename Value="..\..\Math\Raw\ClpNat256.pas"/>
         <UnitName Value="ClpNat256"/>
-      </Item226>
-      <Item227>
+      </Item225>
+      <Item226>
         <Filename Value="..\..\Math\Raw\ClpNat320.pas"/>
         <UnitName Value="ClpNat320"/>
-      </Item227>
-      <Item228>
+      </Item226>
+      <Item227>
         <Filename Value="..\..\Crypto\Engines\ClpAesLightEngine.pas"/>
         <UnitName Value="ClpAesLightEngine"/>
-      </Item228>
-      <Item229>
+      </Item227>
+      <Item228>
         <Filename Value="..\..\Interfaces\ClpIAesLightEngine.pas"/>
         <UnitName Value="ClpIAesLightEngine"/>
-      </Item229>
-      <Item230>
+      </Item228>
+      <Item229>
         <Filename Value="..\..\Crypto\EC\ClpCustomNamedCurves.pas"/>
         <UnitName Value="ClpCustomNamedCurves"/>
-      </Item230>
-      <Item231>
+      </Item229>
+      <Item230>
         <Filename Value="..\..\Math\Raw\ClpNat384.pas"/>
         <UnitName Value="ClpNat384"/>
-      </Item231>
-      <Item232>
+      </Item230>
+      <Item231>
         <Filename Value="..\..\Math\Raw\ClpNat192.pas"/>
         <UnitName Value="ClpNat192"/>
-      </Item232>
-      <Item233>
+      </Item231>
+      <Item232>
         <Filename Value="..\..\Math\Raw\ClpNat512.pas"/>
         <UnitName Value="ClpNat512"/>
-      </Item233>
-      <Item234>
+      </Item232>
+      <Item233>
         <Filename Value="..\..\Math\Raw\ClpInterleave.pas"/>
         <UnitName Value="ClpInterleave"/>
-      </Item234>
-      <Item235>
+      </Item233>
+      <Item234>
         <Filename Value="..\..\Asn1\Bsi\ClpBsiObjectIdentifiers.pas"/>
         <UnitName Value="ClpBsiObjectIdentifiers"/>
-      </Item235>
-      <Item236>
+      </Item234>
+      <Item235>
         <Filename Value="..\..\Asn1\Eac\ClpEacObjectIdentifiers.pas"/>
         <UnitName Value="ClpEacObjectIdentifiers"/>
-      </Item236>
-      <Item237>
+      </Item235>
+      <Item236>
         <Filename Value="..\..\Interfaces\ClpIDsaExt.pas"/>
         <UnitName Value="ClpIDsaExt"/>
-      </Item237>
-      <Item238>
+      </Item236>
+      <Item237>
         <Filename Value="..\..\Interfaces\ClpISchnorrDigestSigner.pas"/>
         <UnitName Value="ClpISchnorrDigestSigner"/>
-      </Item238>
-      <Item239>
+      </Item237>
+      <Item238>
         <Filename Value="..\..\Interfaces\ClpIECSchnorrSipaSigner.pas"/>
         <UnitName Value="ClpIECSchnorrSipaSigner"/>
-      </Item239>
-      <Item240>
+      </Item238>
+      <Item239>
         <Filename Value="..\..\Crypto\Signers\ClpECSchnorrSipaSigner.pas"/>
         <UnitName Value="ClpECSchnorrSipaSigner"/>
-      </Item240>
-      <Item241>
+      </Item239>
+      <Item240>
         <Filename Value="..\..\Crypto\Signers\ClpSchnorrDigestSigner.pas"/>
         <UnitName Value="ClpSchnorrDigestSigner"/>
-      </Item241>
-      <Item242>
+      </Item240>
+      <Item241>
         <Filename Value="..\..\Interfaces\ClpISchnorr.pas"/>
         <UnitName Value="ClpISchnorr"/>
-      </Item242>
-      <Item243>
+      </Item241>
+      <Item242>
         <Filename Value="..\..\Interfaces\ClpISchnorrExt.pas"/>
         <UnitName Value="ClpISchnorrExt"/>
-      </Item243>
-      <Item244>
+      </Item242>
+      <Item243>
         <Filename Value="..\..\Crypto\Engines\ClpBlowfishEngine.pas"/>
         <UnitName Value="ClpBlowfishEngine"/>
-      </Item244>
-      <Item245>
+      </Item243>
+      <Item244>
         <Filename Value="..\..\Interfaces\ClpIBlowfishEngine.pas"/>
         <UnitName Value="ClpIBlowfishEngine"/>
-      </Item245>
-      <Item246>
+      </Item244>
+      <Item245>
         <Filename Value="..\..\Math\EC\ClpECC.pas"/>
         <UnitName Value="ClpECC"/>
-      </Item246>
-      <Item247>
+      </Item245>
+      <Item246>
         <Filename Value="..\..\Asn1\ClpAsn1Objects.pas"/>
         <UnitName Value="ClpAsn1Objects"/>
-      </Item247>
-      <Item248>
+      </Item246>
+      <Item247>
         <Filename Value="..\..\Crypto\Signers\SignersEncodings\ClpSignersEncodings.pas"/>
         <UnitName Value="ClpSignersEncodings"/>
-      </Item248>
-      <Item249>
+      </Item247>
+      <Item248>
         <Filename Value="..\..\Interfaces\ClpISignersEncodings.pas"/>
         <UnitName Value="ClpISignersEncodings"/>
-      </Item249>
-      <Item250>
+      </Item248>
+      <Item249>
         <Filename Value="..\..\Utils\Encoders\ClpEncoders.pas"/>
         <UnitName Value="ClpEncoders"/>
-      </Item250>
-      <Item251>
+      </Item249>
+      <Item250>
         <Filename Value="..\..\Math\EC\Custom\Sec\ClpSecT283Custom.pas"/>
         <UnitName Value="ClpSecT283Custom"/>
-      </Item251>
-      <Item252>
+      </Item250>
+      <Item251>
         <Filename Value="..\..\Math\EC\Custom\Sec\ClpSecP521R1Custom.pas"/>
         <UnitName Value="ClpSecP521R1Custom"/>
-      </Item252>
-      <Item253>
+      </Item251>
+      <Item252>
         <Filename Value="..\..\Math\EC\Custom\Sec\ClpSecP384R1Custom.pas"/>
         <UnitName Value="ClpSecP384R1Custom"/>
-      </Item253>
-      <Item254>
+      </Item252>
+      <Item253>
         <Filename Value="..\..\Math\EC\Custom\Sec\ClpSecP256R1Custom.pas"/>
         <UnitName Value="ClpSecP256R1Custom"/>
-      </Item254>
-      <Item255>
+      </Item253>
+      <Item254>
         <Filename Value="..\..\Math\EC\Custom\Sec\ClpSecP256K1Custom.pas"/>
         <UnitName Value="ClpSecP256K1Custom"/>
-      </Item255>
-      <Item256>
+      </Item254>
+      <Item255>
         <Filename Value="..\..\Interfaces\ClpIX9ECC.pas"/>
         <UnitName Value="ClpIX9ECC"/>
-      </Item256>
-      <Item257>
+      </Item255>
+      <Item256>
         <Filename Value="..\..\Asn1\X9\ClpX9ECC.pas"/>
         <UnitName Value="ClpX9ECC"/>
-      </Item257>
-      <Item258>
+      </Item256>
+      <Item257>
         <Filename Value="..\..\Interfaces\ClpIAsn1Objects.pas"/>
         <UnitName Value="ClpIAsn1Objects"/>
-      </Item258>
-      <Item259>
+      </Item257>
+      <Item258>
         <Filename Value="..\..\Crypto\Modes\ClpBlockCipherModes.pas"/>
         <UnitName Value="ClpBlockCipherModes"/>
-      </Item259>
-      <Item260>
+      </Item258>
+      <Item259>
         <Filename Value="..\..\Math\EC\ClpECCurveConstants.pas"/>
         <UnitName Value="ClpECCurveConstants"/>
-      </Item260>
-      <Item261>
+      </Item259>
+      <Item260>
         <Filename Value="..\..\Interfaces\ClpIBlockCipherModes.pas"/>
         <UnitName Value="ClpIBlockCipherModes"/>
-      </Item261>
-      <Item262>
+      </Item260>
+      <Item261>
         <Filename Value="..\..\Interfaces\ClpIPaddingModes.pas"/>
         <UnitName Value="ClpIPaddingModes"/>
-      </Item262>
-      <Item263>
+      </Item261>
+      <Item262>
         <Filename Value="..\..\Interfaces\ClpISecP256K1Custom.pas"/>
         <UnitName Value="ClpISecP256K1Custom"/>
-      </Item263>
-      <Item264>
+      </Item262>
+      <Item263>
         <Filename Value="..\..\Interfaces\ClpISecP256R1Custom.pas"/>
         <UnitName Value="ClpISecP256R1Custom"/>
-      </Item264>
-      <Item265>
+      </Item263>
+      <Item264>
         <Filename Value="..\..\Interfaces\ClpISecP384R1Custom.pas"/>
         <UnitName Value="ClpISecP384R1Custom"/>
-      </Item265>
-      <Item266>
+      </Item264>
+      <Item265>
         <Filename Value="..\..\Interfaces\ClpISecP521R1Custom.pas"/>
         <UnitName Value="ClpISecP521R1Custom"/>
-      </Item266>
-      <Item267>
+      </Item265>
+      <Item266>
         <Filename Value="..\..\Interfaces\ClpISecT283Custom.pas"/>
         <UnitName Value="ClpISecT283Custom"/>
-      </Item267>
-      <Item268>
+      </Item266>
+      <Item267>
         <Filename Value="..\..\Crypto\Paddings\ClpPaddingModes.pas"/>
         <UnitName Value="ClpPaddingModes"/>
-      </Item268>
-      <Item269>
+      </Item267>
+      <Item268>
         <Filename Value="..\..\Interfaces\ClpIECC.pas"/>
         <UnitName Value="ClpIECC"/>
-      </Item269>
-      <Item270>
+      </Item268>
+      <Item269>
         <Filename Value="..\..\Interfaces\ClpISpeckEngine.pas"/>
         <UnitName Value="ClpISpeckEngine"/>
-      </Item270>
-      <Item271>
+      </Item269>
+      <Item270>
         <Filename Value="..\..\Crypto\Engines\ClpSpeckEngine.pas"/>
         <UnitName Value="ClpSpeckEngine"/>
-      </Item271>
-      <Item272>
+      </Item270>
+      <Item271>
         <Filename Value="..\..\Interfaces\ClpIBufferedStreamCipher.pas"/>
         <UnitName Value="ClpIBufferedStreamCipher"/>
-      </Item272>
-      <Item273>
+      </Item271>
+      <Item272>
         <Filename Value="..\..\Interfaces\ClpIChaChaEngine.pas"/>
         <UnitName Value="ClpIChaChaEngine"/>
-      </Item273>
-      <Item274>
+      </Item272>
+      <Item273>
         <Filename Value="..\..\Interfaces\ClpIXSalsa20Engine.pas"/>
         <UnitName Value="ClpIXSalsa20Engine"/>
-      </Item274>
-      <Item275>
+      </Item273>
+      <Item274>
         <Filename Value="..\..\Interfaces\ClpISalsa20Engine.pas"/>
         <UnitName Value="ClpISalsa20Engine"/>
-      </Item275>
-      <Item276>
+      </Item274>
+      <Item275>
         <Filename Value="..\..\Crypto\ClpBufferedStreamCipher.pas"/>
         <UnitName Value="ClpBufferedStreamCipher"/>
-      </Item276>
-      <Item277>
+      </Item275>
+      <Item276>
         <Filename Value="..\..\Crypto\Engines\ClpSalsa20Engine.pas"/>
         <UnitName Value="ClpSalsa20Engine"/>
-      </Item277>
-      <Item278>
+      </Item276>
+      <Item277>
         <Filename Value="..\..\Crypto\Engines\ClpXSalsa20Engine.pas"/>
         <UnitName Value="ClpXSalsa20Engine"/>
-      </Item278>
-      <Item279>
+      </Item277>
+      <Item278>
         <Filename Value="..\..\Crypto\Engines\ClpChaChaEngine.pas"/>
         <UnitName Value="ClpChaChaEngine"/>
-      </Item279>
-      <Item280>
+      </Item278>
+      <Item279>
         <Filename Value="..\..\Interfaces\ClpIRijndaelEngine.pas"/>
         <UnitName Value="ClpIRijndaelEngine"/>
-      </Item280>
-      <Item281>
+      </Item279>
+      <Item280>
         <Filename Value="..\..\Crypto\Engines\ClpRijndaelEngine.pas"/>
         <UnitName Value="ClpRijndaelEngine"/>
-      </Item281>
-      <Item282>
+      </Item280>
+      <Item281>
         <Filename Value="..\..\Interfaces\ClpIIESParameterSpec.pas"/>
         <UnitName Value="ClpIIESParameterSpec"/>
-      </Item282>
-      <Item283>
+      </Item281>
+      <Item282>
         <Filename Value="..\..\Interfaces\ClpIAlgorithmParameterSpec.pas"/>
         <UnitName Value="ClpIAlgorithmParameterSpec"/>
-      </Item283>
-      <Item284>
+      </Item282>
+      <Item283>
         <Filename Value="..\..\Crypto\Parameters\ClpIESParameterSpec.pas"/>
         <UnitName Value="ClpIESParameterSpec"/>
-      </Item284>
-      <Item285>
+      </Item283>
+      <Item284>
         <Filename Value="..\..\Math\EC\Custom\Djb\ClpCurve25519Custom.pas"/>
         <UnitName Value="ClpCurve25519Custom"/>
-      </Item285>
-      <Item286>
+      </Item284>
+      <Item285>
         <Filename Value="..\..\Interfaces\ClpICurve25519Custom.pas"/>
         <UnitName Value="ClpICurve25519Custom"/>
-      </Item286>
-      <Item287>
+      </Item285>
+      <Item286>
         <Filename Value="..\..\Crypto\Engines\ClpSpeckLegacyEngine.pas"/>
         <UnitName Value="ClpSpeckLegacyEngine"/>
-      </Item287>
-      <Item288>
+      </Item286>
+      <Item287>
         <Filename Value="..\..\Interfaces\ClpISpeckLegacyEngine.pas"/>
         <UnitName Value="ClpISpeckLegacyEngine"/>
-      </Item288>
-      <Item289>
+      </Item287>
+      <Item288>
         <Filename Value="..\..\Interfaces\ClpIEd25519.pas"/>
         <UnitName Value="ClpIEd25519"/>
-      </Item289>
-      <Item290>
+      </Item288>
+      <Item289>
         <Filename Value="..\..\Interfaces\ClpIEd25519Blake2B.pas"/>
         <UnitName Value="ClpIEd25519Blake2B"/>
-      </Item290>
-      <Item291>
+      </Item289>
+      <Item290>
         <Filename Value="..\..\Math\EC\Rfc7748\ClpX25519Field.pas"/>
         <UnitName Value="ClpX25519Field"/>
-      </Item291>
-      <Item292>
+      </Item290>
+      <Item291>
         <Filename Value="..\..\Math\EC\Rfc8032\ClpEd25519.pas"/>
         <UnitName Value="ClpEd25519"/>
-      </Item292>
-      <Item293>
+      </Item291>
+      <Item292>
         <Filename Value="..\..\Math\EC\Rfc8032\ClpEd25519Blake2B.pas"/>
         <UnitName Value="ClpEd25519Blake2B"/>
-      </Item293>
-      <Item294>
+      </Item292>
+      <Item293>
         <Filename Value="..\..\Math\EC\Rfc7748\ClpX25519.pas"/>
         <UnitName Value="ClpX25519"/>
-      </Item294>
-      <Item295>
+      </Item293>
+      <Item294>
         <Filename Value="..\..\Asn1\Edec\ClpEdECObjectIdentifiers.pas"/>
         <UnitName Value="ClpEdECObjectIdentifiers"/>
-      </Item295>
-      <Item296>
+      </Item294>
+      <Item295>
         <Filename Value="..\..\Interfaces\ClpIEd25519CtxBlake2BSigner.pas"/>
         <UnitName Value="ClpIEd25519CtxBlake2BSigner"/>
-      </Item296>
-      <Item297>
+      </Item295>
+      <Item296>
         <Filename Value="..\..\Interfaces\ClpIEd25519PhBlake2BSigner.pas"/>
         <UnitName Value="ClpIEd25519PhBlake2BSigner"/>
-      </Item297>
-      <Item298>
+      </Item296>
+      <Item297>
         <Filename Value="..\..\Interfaces\ClpIEd25519PhSigner.pas"/>
         <UnitName Value="ClpIEd25519PhSigner"/>
-      </Item298>
-      <Item299>
+      </Item297>
+      <Item298>
         <Filename Value="..\..\Interfaces\ClpIEd25519CtxSigner.pas"/>
         <UnitName Value="ClpIEd25519CtxSigner"/>
-      </Item299>
-      <Item300>
+      </Item298>
+      <Item299>
         <Filename Value="..\..\Interfaces\ClpIEd25519Blake2BSigner.pas"/>
         <UnitName Value="ClpIEd25519Blake2BSigner"/>
-      </Item300>
-      <Item301>
+      </Item299>
+      <Item300>
         <Filename Value="..\..\Interfaces\ClpIEd25519Signer.pas"/>
         <UnitName Value="ClpIEd25519Signer"/>
-      </Item301>
-      <Item302>
+      </Item300>
+      <Item301>
         <Filename Value="..\..\Interfaces\ClpIEd25519Blake2BKeyGenerationParameters.pas"/>
         <UnitName Value="ClpIEd25519Blake2BKeyGenerationParameters"/>
-      </Item302>
-      <Item303>
+      </Item301>
+      <Item302>
         <Filename Value="..\..\Interfaces\ClpIEd25519KeyGenerationParameters.pas"/>
         <UnitName Value="ClpIEd25519KeyGenerationParameters"/>
-      </Item303>
-      <Item304>
+      </Item302>
+      <Item303>
         <Filename Value="..\..\Interfaces\ClpIX25519KeyGenerationParameters.pas"/>
         <UnitName Value="ClpIX25519KeyGenerationParameters"/>
-      </Item304>
-      <Item305>
+      </Item303>
+      <Item304>
         <Filename Value="..\..\Interfaces\ClpIEd25519Blake2BKeyPairGenerator.pas"/>
         <UnitName Value="ClpIEd25519Blake2BKeyPairGenerator"/>
-      </Item305>
-      <Item306>
+      </Item304>
+      <Item305>
         <Filename Value="..\..\Interfaces\ClpIEd25519KeyPairGenerator.pas"/>
         <UnitName Value="ClpIEd25519KeyPairGenerator"/>
-      </Item306>
-      <Item307>
+      </Item305>
+      <Item306>
         <Filename Value="..\..\Interfaces\ClpIX25519KeyPairGenerator.pas"/>
         <UnitName Value="ClpIX25519KeyPairGenerator"/>
-      </Item307>
-      <Item308>
+      </Item306>
+      <Item307>
         <Filename Value="..\..\Interfaces\ClpIEd25519Blake2BPrivateKeyParameters.pas"/>
         <UnitName Value="ClpIEd25519Blake2BPrivateKeyParameters"/>
-      </Item308>
-      <Item309>
+      </Item307>
+      <Item308>
         <Filename Value="..\..\Interfaces\ClpIEd25519Blake2BPublicKeyParameters.pas"/>
         <UnitName Value="ClpIEd25519Blake2BPublicKeyParameters"/>
-      </Item309>
-      <Item310>
+      </Item308>
+      <Item309>
         <Filename Value="..\..\Interfaces\ClpIEd25519PrivateKeyParameters.pas"/>
         <UnitName Value="ClpIEd25519PrivateKeyParameters"/>
-      </Item310>
-      <Item311>
+      </Item309>
+      <Item310>
         <Filename Value="..\..\Interfaces\ClpIEd25519PublicKeyParameters.pas"/>
         <UnitName Value="ClpIEd25519PublicKeyParameters"/>
-      </Item311>
-      <Item312>
+      </Item310>
+      <Item311>
         <Filename Value="..\..\Interfaces\ClpIX25519PublicKeyParameters.pas"/>
         <UnitName Value="ClpIX25519PublicKeyParameters"/>
-      </Item312>
-      <Item313>
+      </Item311>
+      <Item312>
         <Filename Value="..\..\Interfaces\ClpIX25519PrivateKeyParameters.pas"/>
         <UnitName Value="ClpIX25519PrivateKeyParameters"/>
-      </Item313>
-      <Item314>
+      </Item312>
+      <Item313>
         <Filename Value="..\..\Interfaces\ClpIX25519Agreement.pas"/>
         <UnitName Value="ClpIX25519Agreement"/>
-      </Item314>
-      <Item315>
+      </Item313>
+      <Item314>
         <Filename Value="..\..\Interfaces\ClpIRawAgreement.pas"/>
         <UnitName Value="ClpIRawAgreement"/>
-      </Item315>
-      <Item316>
+      </Item314>
+      <Item315>
         <Filename Value="..\..\Crypto\Agreement\ClpX25519Agreement.pas"/>
         <UnitName Value="ClpX25519Agreement"/>
-      </Item316>
-      <Item317>
+      </Item315>
+      <Item316>
         <Filename Value="..\..\Crypto\Parameters\ClpEd25519Blake2BKeyGenerationParameters.pas"/>
         <UnitName Value="ClpEd25519Blake2BKeyGenerationParameters"/>
-      </Item317>
-      <Item318>
+      </Item316>
+      <Item317>
         <Filename Value="..\..\Crypto\Parameters\ClpEd25519KeyGenerationParameters.pas"/>
         <UnitName Value="ClpEd25519KeyGenerationParameters"/>
-      </Item318>
-      <Item319>
+      </Item317>
+      <Item318>
         <Filename Value="..\..\Crypto\Parameters\ClpX25519KeyGenerationParameters.pas"/>
         <UnitName Value="ClpX25519KeyGenerationParameters"/>
-      </Item319>
-      <Item320>
+      </Item318>
+      <Item319>
         <Filename Value="..\..\Crypto\Parameters\ClpEd25519Blake2BPrivateKeyParameters.pas"/>
         <UnitName Value="ClpEd25519Blake2BPrivateKeyParameters"/>
-      </Item320>
-      <Item321>
+      </Item319>
+      <Item320>
         <Filename Value="..\..\Crypto\Parameters\ClpEd25519Blake2BPublicKeyParameters.pas"/>
         <UnitName Value="ClpEd25519Blake2BPublicKeyParameters"/>
-      </Item321>
-      <Item322>
+      </Item320>
+      <Item321>
         <Filename Value="..\..\Crypto\Parameters\ClpEd25519PublicKeyParameters.pas"/>
         <UnitName Value="ClpEd25519PublicKeyParameters"/>
-      </Item322>
-      <Item323>
+      </Item321>
+      <Item322>
         <Filename Value="..\..\Crypto\Parameters\ClpEd25519PrivateKeyParameters.pas"/>
         <UnitName Value="ClpEd25519PrivateKeyParameters"/>
-      </Item323>
-      <Item324>
+      </Item322>
+      <Item323>
         <Filename Value="..\..\Crypto\Parameters\ClpX25519PublicKeyParameters.pas"/>
         <UnitName Value="ClpX25519PublicKeyParameters"/>
-      </Item324>
-      <Item325>
+      </Item323>
+      <Item324>
         <Filename Value="..\..\Crypto\Parameters\ClpX25519PrivateKeyParameters.pas"/>
         <UnitName Value="ClpX25519PrivateKeyParameters"/>
-      </Item325>
-      <Item326>
+      </Item324>
+      <Item325>
         <Filename Value="..\..\Crypto\Generators\ClpEd25519Blake2BKeyPairGenerator.pas"/>
         <UnitName Value="ClpEd25519Blake2BKeyPairGenerator"/>
-      </Item326>
-      <Item327>
+      </Item325>
+      <Item326>
         <Filename Value="..\..\Crypto\Generators\ClpEd25519KeyPairGenerator.pas"/>
         <UnitName Value="ClpEd25519KeyPairGenerator"/>
-      </Item327>
-      <Item328>
+      </Item326>
+      <Item327>
         <Filename Value="..\..\Crypto\Generators\ClpX25519KeyPairGenerator.pas"/>
         <UnitName Value="ClpX25519KeyPairGenerator"/>
-      </Item328>
-      <Item329>
+      </Item327>
+      <Item328>
         <Filename Value="..\..\Crypto\Signers\ClpEd25519PhBlake2BSigner.pas"/>
         <UnitName Value="ClpEd25519PhBlake2BSigner"/>
-      </Item329>
-      <Item330>
+      </Item328>
+      <Item329>
         <Filename Value="..\..\Crypto\Signers\ClpEd25519PhSigner.pas"/>
         <UnitName Value="ClpEd25519PhSigner"/>
-      </Item330>
-      <Item331>
+      </Item329>
+      <Item330>
         <Filename Value="..\..\Crypto\Signers\ClpEd25519Signer.pas"/>
         <UnitName Value="ClpEd25519Signer"/>
-      </Item331>
-      <Item332>
+      </Item330>
+      <Item331>
         <Filename Value="..\..\Crypto\Signers\ClpEd25519CtxBlake2BSigner.pas"/>
         <UnitName Value="ClpEd25519CtxBlake2BSigner"/>
-      </Item332>
-      <Item333>
+      </Item331>
+      <Item332>
         <Filename Value="..\..\Crypto\Signers\ClpEd25519CtxSigner.pas"/>
         <UnitName Value="ClpEd25519CtxSigner"/>
-      </Item333>
-      <Item334>
+      </Item332>
+      <Item333>
         <Filename Value="..\..\Crypto\Signers\ClpEd25519Blake2BSigner.pas"/>
         <UnitName Value="ClpEd25519Blake2BSigner"/>
+      </Item333>
+      <Item334>
+        <Filename Value="..\..\Asn1\TeleTrust\ClpTeleTrusTNamedCurves.pas"/>
+        <UnitName Value="ClpTeleTrusTNamedCurves"/>
       </Item334>
+      <Item335>
+        <Filename Value="..\..\Security\ClpAgreementUtilities.pas"/>
+        <UnitName Value="ClpAgreementUtilities"/>
+      </Item335>
+      <Item336>
+        <Filename Value="..\..\Interfaces\ClpIKdf1BytesGenerator.pas"/>
+        <UnitName Value="ClpIKdf1BytesGenerator"/>
+      </Item336>
+      <Item337>
+        <Filename Value="..\..\Crypto\Generators\ClpKdf1BytesGenerator.pas"/>
+        <UnitName Value="ClpKdf1BytesGenerator"/>
+      </Item337>
+      <Item338>
+        <Filename Value="..\..\Interfaces\ClpIArgon2ParametersGenerator.pas"/>
+        <UnitName Value="ClpIArgon2ParametersGenerator"/>
+      </Item338>
+      <Item339>
+        <Filename Value="..\..\Crypto\Generators\ClpArgon2ParametersGenerator.pas"/>
+        <UnitName Value="ClpArgon2ParametersGenerator"/>
+      </Item339>
+      <Item340>
+        <Filename Value="..\..\Interfaces\ClpIScryptParametersGenerator.pas"/>
+        <UnitName Value="ClpIScryptParametersGenerator"/>
+      </Item340>
+      <Item341>
+        <Filename Value="..\..\Crypto\Generators\ClpScryptParametersGenerator.pas"/>
+        <UnitName Value="ClpScryptParametersGenerator"/>
+      </Item341>
     </Files>
     <RequiredPkgs Count="4">
       <Item1>
@@ -1371,12 +1399,12 @@ Thanks to Sphere 10 Software (http://www.sphere10.com/) for sponsoring the devel
       </Item1>
       <Item2>
         <PackageName Value="HashLib4PascalPackage"/>
-        <MaxVersion Major="2" Minor="4"/>
-        <MinVersion Major="2" Minor="5" Valid="True"/>
-      </Item2>
-      <Item3>
+        <MaxVersion Major="3" Minor="5"/>
+        <MinVersion Major="3" Minor="5" Valid="True"/>
+      </Item1>
+      <Item2>
         <PackageName Value="SimpleBaseLib4PascalPackage"/>
-        <MaxVersion Major="1" Minor="2"/>
+        <MaxVersion Major="1" Minor="4"/>
         <MinVersion Major="1" Minor="4" Valid="True"/>
       </Item3>
       <Item4>

+ 16 - 14
CryptoLib/src/Packages/FPC/CryptoLib4PascalPackage.pas

@@ -79,19 +79,18 @@ uses
   ClpIECDHCBasicAgreement, ClpHMacDsaKCalculator, ClpIHMacDsaKCalculator, 
   ClpHkdfBytesGenerator, ClpIHkdfBytesGenerator, ClpHkdfParameters, 
   ClpIHkdfParameters, ClpDsaParameterGenerationParameters, 
-  ClpIDsaParameterGenerationParameters, ClpValidityPrecompInfo, 
-  ClpIValidityPrecompInfo, ClpDsaParametersGenerator, ClpDsaParameter, 
-  ClpIDsaParameter, ClpIKeyEncoder, ClpIDsaParametersGenerator, 
-  ClpIPreCompCallBack, ClpNistNamedCurves, ClpNat256, ClpNat320, 
-  ClpAesLightEngine, ClpIAesLightEngine, ClpCustomNamedCurves, ClpNat384, 
-  ClpNat192, ClpNat512, ClpInterleave, ClpBsiObjectIdentifiers, 
-  ClpEacObjectIdentifiers, ClpIDsaExt, ClpISchnorrDigestSigner, 
-  ClpIECSchnorrSipaSigner, ClpECSchnorrSipaSigner, ClpSchnorrDigestSigner, 
-  ClpISchnorr, ClpISchnorrExt, ClpBlowfishEngine, ClpIBlowfishEngine, ClpECC, 
-  ClpAsn1Objects, ClpSignersEncodings, ClpISignersEncodings, ClpEncoders, 
-  ClpSecT283Custom, ClpSecP521R1Custom, ClpSecP384R1Custom, 
-  ClpSecP256R1Custom, ClpSecP256K1Custom, ClpIX9ECC, ClpX9ECC, 
-  ClpIAsn1Objects, ClpBlockCipherModes, ClpECCurveConstants, 
+  ClpIDsaParameterGenerationParameters, ClpIValidityPrecompInfo, 
+  ClpDsaParametersGenerator, ClpDsaParameter, ClpIDsaParameter, 
+  ClpIKeyEncoder, ClpIDsaParametersGenerator, ClpIPreCompCallBack, 
+  ClpNistNamedCurves, ClpNat256, ClpNat320, ClpAesLightEngine, 
+  ClpIAesLightEngine, ClpCustomNamedCurves, ClpNat384, ClpNat192, ClpNat512, 
+  ClpInterleave, ClpBsiObjectIdentifiers, ClpEacObjectIdentifiers, ClpIDsaExt, 
+  ClpISchnorrDigestSigner, ClpIECSchnorrSipaSigner, ClpECSchnorrSipaSigner, 
+  ClpSchnorrDigestSigner, ClpISchnorr, ClpISchnorrExt, ClpBlowfishEngine, 
+  ClpIBlowfishEngine, ClpECC, ClpAsn1Objects, ClpSignersEncodings, 
+  ClpISignersEncodings, ClpEncoders, ClpSecT283Custom, ClpSecP521R1Custom, 
+  ClpSecP384R1Custom, ClpSecP256R1Custom, ClpSecP256K1Custom, ClpIX9ECC, 
+  ClpX9ECC, ClpIAsn1Objects, ClpBlockCipherModes, ClpECCurveConstants, 
   ClpIBlockCipherModes, ClpIPaddingModes, ClpISecP256K1Custom, 
   ClpISecP256R1Custom, ClpISecP384R1Custom, ClpISecP521R1Custom, 
   ClpISecT283Custom, ClpPaddingModes, ClpIECC, ClpISpeckEngine, 
@@ -120,7 +119,10 @@ uses
   ClpEd25519Blake2BKeyPairGenerator, ClpEd25519KeyPairGenerator, 
   ClpX25519KeyPairGenerator, ClpEd25519PhBlake2BSigner, ClpEd25519PhSigner, 
   ClpEd25519Signer, ClpEd25519CtxBlake2BSigner, ClpEd25519CtxSigner, 
-  ClpEd25519Blake2BSigner;
+  ClpEd25519Blake2BSigner, ClpTeleTrusTNamedCurves, ClpAgreementUtilities, 
+  ClpIKdf1BytesGenerator, ClpKdf1BytesGenerator, 
+  ClpIArgon2ParametersGenerator, ClpArgon2ParametersGenerator, 
+  ClpIScryptParametersGenerator, ClpScryptParametersGenerator;
 
 implementation
 

+ 171 - 0
CryptoLib/src/Security/ClpAgreementUtilities.pas

@@ -0,0 +1,171 @@
+{ *********************************************************************************** }
+{ *                              CryptoLib Library                                  * }
+{ *                Copyright (c) 2018 - 20XX Ugochukwu Mmaduekwe                    * }
+{ *                 Github Repository <https://github.com/Xor-el>                   * }
+
+{ *  Distributed under the MIT software license, see the accompanying file LICENSE  * }
+{ *          or visit http://www.opensource.org/licenses/mit-license.php.           * }
+
+{ *                              Acknowledgements:                                  * }
+{ *                                                                                 * }
+{ *      Thanks to Sphere 10 Software (http://www.sphere10.com/) for sponsoring     * }
+{ *                           development of this library                           * }
+
+{ * ******************************************************************************* * }
+
+(* &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&& *)
+
+unit ClpAgreementUtilities;
+
+{$I ..\Include\CryptoLib.inc}
+
+interface
+
+uses
+  SysUtils,
+  Generics.Collections,
+  ClpIBasicAgreement,
+  ClpECDHBasicAgreement,
+  ClpIECDHBasicAgreement,
+  ClpECDHCBasicAgreement,
+  ClpIECDHCBasicAgreement,
+  ClpX25519Agreement,
+  ClpIX25519Agreement,
+  ClpIRawAgreement,
+  ClpEdECObjectIdentifiers,
+  ClpIAsn1Objects,
+  ClpCryptoLibTypes;
+
+resourcestring
+  SUnRecognizedRawAgreementAlgorithm =
+    'Raw Agreement Algorithm "%s" Not Recognised.';
+  SUnRecognizedBasicAgreementAlgorithm =
+    'Basic Agreement Algorithm "%s" Not Recognised.';
+
+type
+
+  /// <summary>
+  /// Utility class for creating IBasicAgreement objects from their
+  /// names/Oids
+  /// </summary>
+  TAgreementUtilities = class sealed(TObject)
+
+  strict private
+    class var
+
+      Falgorithms: TDictionary<String, String>;
+
+    class function GetMechanism(const algorithm: String): String;
+      static; inline;
+
+    class procedure Boot(); static;
+    class constructor CreateAgreementUtilities();
+    class destructor DestroyAgreementUtilities();
+
+  public
+    class function GetBasicAgreement(const algorithm: String)
+      : IBasicAgreement; static;
+
+    class function GetRawAgreement(const oid: IDerObjectIdentifier)
+      : IRawAgreement; overload; static; inline;
+
+    class function GetRawAgreement(const algorithm: String): IRawAgreement;
+      overload; static;
+
+    class function GetAlgorithmName(const oid: IDerObjectIdentifier): String;
+      static; inline;
+
+  end;
+
+implementation
+
+{ TAgreementUtilities }
+
+class procedure TAgreementUtilities.Boot;
+begin
+  Falgorithms := TDictionary<string, string>.Create();
+  Falgorithms.Add(TEdECObjectIdentifiers.id_X25519.Id, 'X25519');
+end;
+
+class constructor TAgreementUtilities.CreateAgreementUtilities;
+begin
+  TAgreementUtilities.Boot;
+end;
+
+class destructor TAgreementUtilities.DestroyAgreementUtilities;
+begin
+  Falgorithms.Free;
+end;
+
+class function TAgreementUtilities.GetMechanism(const algorithm
+  : String): String;
+var
+  upper, mechanism: String;
+begin
+  upper := UpperCase(algorithm);
+  if Falgorithms.TryGetValue(upper, mechanism) then
+  begin
+    result := mechanism
+  end
+  else
+  begin
+    result := upper;
+  end;
+end;
+
+class function TAgreementUtilities.GetAlgorithmName
+  (const oid: IDerObjectIdentifier): String;
+begin
+  if not(Falgorithms.TryGetValue(oid.Id, result)) then
+  begin
+    result := '';
+  end;
+end;
+
+class function TAgreementUtilities.GetBasicAgreement(const algorithm: String)
+  : IBasicAgreement;
+var
+  mechanism: String;
+begin
+  mechanism := GetMechanism(algorithm);
+
+  if (mechanism = 'ECDH') then
+  begin
+    result := TECDHBasicAgreement.Create() as IECDHBasicAgreement;
+    Exit;
+  end;
+
+  if ((mechanism = 'ECDHC') or (mechanism = 'ECCDH')) then
+  begin
+    result := TECDHCBasicAgreement.Create() as IECDHCBasicAgreement;
+    Exit;
+  end;
+
+  raise ESecurityUtilityCryptoLibException.CreateResFmt
+    (@SUnRecognizedBasicAgreementAlgorithm, [algorithm]);
+end;
+
+class function TAgreementUtilities.GetRawAgreement(const algorithm: String)
+  : IRawAgreement;
+var
+  mechanism: String;
+begin
+  mechanism := GetMechanism(algorithm);
+
+  if (mechanism = 'X25519') then
+  begin
+    result := TX25519Agreement.Create() as IX25519Agreement;
+    Exit;
+  end;
+
+  raise ESecurityUtilityCryptoLibException.CreateResFmt
+    (@SUnRecognizedRawAgreementAlgorithm, [algorithm]);
+end;
+
+class function TAgreementUtilities.GetRawAgreement
+  (const oid: IDerObjectIdentifier): IRawAgreement;
+begin
+  result := GetRawAgreement(oid.Id);
+end;
+
+end.

+ 1 - 1
CryptoLib/src/Security/ClpCipherUtilities.pas

@@ -55,7 +55,7 @@ uses
 resourcestring
   SMechanismNil = 'Mechanism Cannot be Nil';
   SAlgorithmNil = 'Algorithm Cannot be Nil';
-  SUnRecognizedCipher = '"Cipher " %s Not Recognised.';
+  SUnRecognizedCipher = 'Cipher "%s" Not Recognised.';
   SSICModeWarning =
     'Warning: SIC-Mode Can Become a TwoTime-Pad if the Blocksize of the Cipher is Too Small. Use a Cipher With a Block Size of at Least 128 bits (e.g. AES)';
   SModeAndPaddingNotNeededStreamCipher =

+ 56 - 36
CryptoLib/src/Security/ClpDigestUtilities.pas

@@ -40,7 +40,7 @@ uses
 
 resourcestring
   SMechanismNil = 'Mechanism Cannot be Nil';
-  SUnRecognizedDigest = '"Digest " %s not recognised.';
+  SUnRecognizedDigest = 'Digest "%s" not recognised.';
 
 type
   TDigestUtilities = class sealed(TObject)
@@ -55,10 +55,11 @@ type
 {$SCOPEDENUMS ON}
     TDigestAlgorithm = (BLAKE2B_160, BLAKE2B_256, BLAKE2B_384, BLAKE2B_512,
       BLAKE2S_128, BLAKE2S_160, BLAKE2S_224, BLAKE2S_256, GOST3411,
-      GOST3411_2012_256, GOST3411_2012_512, MD2, MD4, MD5, NONE, RIPEMD128,
-      RIPEMD160, RIPEMD256, RIPEMD320, SHA_1, SHA_224, SHA_256, SHA_384,
-      SHA_512, SHA_512_224, SHA_512_256, SHA3_224, SHA3_256, SHA3_384, SHA3_512,
-      TIGER, WHIRLPOOL);
+      GOST3411_2012_256, GOST3411_2012_512, KECCAK_224, KECCAK_256, KECCAK_288,
+      KECCAK_384, KECCAK_512, MD2, MD4, MD5, NONE, RIPEMD128, RIPEMD160,
+      RIPEMD256, RIPEMD320, SHA_1, SHA_224, SHA_256, SHA_384, SHA_512,
+      SHA_512_224, SHA_512_256, SHA3_224, SHA3_256, SHA3_384, SHA3_512,
+      SHAKE128, SHAKE256, TIGER, WHIRLPOOL);
 {$SCOPEDENUMS OFF}
   class procedure Boot(); static;
   class constructor CreateDigestUtilities();
@@ -132,63 +133,54 @@ begin
     TDigestAlgorithm.BLAKE2B_160:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateBlake2B_160);
-
         Exit;
       end;
 
     TDigestAlgorithm.BLAKE2B_256:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateBlake2B_256);
-
         Exit;
       end;
 
     TDigestAlgorithm.BLAKE2B_384:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateBlake2B_384);
-
         Exit;
       end;
 
     TDigestAlgorithm.BLAKE2B_512:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateBlake2B_512);
-
         Exit;
       end;
 
     TDigestAlgorithm.BLAKE2S_128:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateBlake2S_128);
-
         Exit;
       end;
 
     TDigestAlgorithm.BLAKE2S_160:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateBlake2S_160);
-
         Exit;
       end;
 
     TDigestAlgorithm.BLAKE2S_224:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateBlake2S_224);
-
         Exit;
       end;
 
     TDigestAlgorithm.BLAKE2S_256:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateBlake2S_256);
-
         Exit;
       end;
 
     TDigestAlgorithm.GOST3411:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateGost());
-
         Exit;
       end;
 
@@ -196,7 +188,6 @@ begin
       begin
         result := TDigest.Create
           (THashFactory.TCrypto.CreateGOST3411_2012_256());
-
         Exit;
       end;
 
@@ -204,28 +195,54 @@ begin
       begin
         result := TDigest.Create
           (THashFactory.TCrypto.CreateGOST3411_2012_512());
+        Exit;
+      end;
 
+    TDigestAlgorithm.KECCAK_224:
+      begin
+        result := TDigest.Create(THashFactory.TCrypto.CreateKeccak_224());
+        Exit;
+      end;
+
+    TDigestAlgorithm.KECCAK_256:
+      begin
+        result := TDigest.Create(THashFactory.TCrypto.CreateKeccak_256());
+        Exit;
+      end;
+
+    TDigestAlgorithm.KECCAK_288:
+      begin
+        result := TDigest.Create(THashFactory.TCrypto.CreateKeccak_288());
+        Exit;
+      end;
+
+    TDigestAlgorithm.KECCAK_384:
+      begin
+        result := TDigest.Create(THashFactory.TCrypto.CreateKeccak_384());
+        Exit;
+      end;
+
+    TDigestAlgorithm.KECCAK_512:
+      begin
+        result := TDigest.Create(THashFactory.TCrypto.CreateKeccak_512());
         Exit;
       end;
 
     TDigestAlgorithm.MD2:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateMD2());
-
         Exit;
       end;
 
     TDigestAlgorithm.MD4:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateMD4());
-
         Exit;
       end;
 
     TDigestAlgorithm.MD5:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateMD5());
-
         Exit;
       end;
 
@@ -233,127 +250,120 @@ begin
       begin
         result := TDigest.Create
           (THashFactory.TNullDigestFactory.CreateNullDigest());
-
         Exit;
       end;
 
     TDigestAlgorithm.RIPEMD128:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateRIPEMD128());
-
         Exit;
       end;
 
     TDigestAlgorithm.RIPEMD160:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateRIPEMD160());
-
         Exit;
       end;
 
     TDigestAlgorithm.RIPEMD256:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateRIPEMD256());
-
         Exit;
       end;
 
     TDigestAlgorithm.RIPEMD320:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateRIPEMD320());
-
         Exit;
       end;
 
     TDigestAlgorithm.SHA_1:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateSHA1());
-
         Exit;
       end;
 
     TDigestAlgorithm.SHA_224:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateSHA2_224());
-
         Exit;
       end;
 
     TDigestAlgorithm.SHA_256:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateSHA2_256());
-
         Exit;
       end;
 
     TDigestAlgorithm.SHA_384:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateSHA2_384());
-
         Exit;
       end;
 
     TDigestAlgorithm.SHA_512:
       begin
-
         result := TDigest.Create(THashFactory.TCrypto.CreateSHA2_512());
-
         Exit;
       end;
 
     TDigestAlgorithm.SHA_512_224:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateSHA2_512_224());
-
         Exit;
       end;
 
     TDigestAlgorithm.SHA_512_256:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateSHA2_512_256());
-
         Exit;
       end;
 
     TDigestAlgorithm.SHA3_224:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateSHA3_224());
-
         Exit;
       end;
 
     TDigestAlgorithm.SHA3_256:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateSHA3_256());
-
         Exit;
       end;
 
     TDigestAlgorithm.SHA3_384:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateSHA3_384());
-
         Exit;
       end;
 
     TDigestAlgorithm.SHA3_512:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateSHA3_512());
+        Exit;
+      end;
+
+    TDigestAlgorithm.SHAKE128:
+      begin
+        result := TDigest.Create(THashFactory.TXOF.CreateShake_128(128));
+        Exit;
+      end;
 
+    TDigestAlgorithm.SHAKE256:
+      begin
+        result := TDigest.Create(THashFactory.TXOF.CreateShake_256(256));
         Exit;
       end;
 
     TDigestAlgorithm.TIGER:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateTiger_3_192);
-
         Exit;
       end;
 
     TDigestAlgorithm.WHIRLPOOL:
       begin
         result := TDigest.Create(THashFactory.TCrypto.CreateWhirlPool);
-
         Exit;
       end
   else
@@ -416,10 +426,18 @@ begin
 
     Falgorithms.Add(TCryptoProObjectIdentifiers.GostR3411.id, 'GOST3411');
 
+    Falgorithms.Add('KECCAK224', 'KECCAK-224');
+    Falgorithms.Add('KECCAK256', 'KECCAK-256');
+    Falgorithms.Add('KECCAK288', 'KECCAK-288');
+    Falgorithms.Add('KECCAK384', 'KECCAK-384');
+    Falgorithms.Add('KECCAK512', 'KECCAK-512');
+
     Falgorithms.Add(TNistObjectIdentifiers.IdSha3_224.id, 'SHA3-224');
     Falgorithms.Add(TNistObjectIdentifiers.IdSha3_256.id, 'SHA3-256');
     Falgorithms.Add(TNistObjectIdentifiers.IdSha3_384.id, 'SHA3-384');
     Falgorithms.Add(TNistObjectIdentifiers.IdSha3_512.id, 'SHA3-512');
+    Falgorithms.Add(TNistObjectIdentifiers.IdShake128.id, 'SHAKE128');
+    Falgorithms.Add(TNistObjectIdentifiers.IdShake256.id, 'SHAKE256');
 
     TMiscObjectIdentifiers.Boot;
 
@@ -453,6 +471,8 @@ begin
     Foids.Add('SHA3-256', TNistObjectIdentifiers.IdSha3_256);
     Foids.Add('SHA3-384', TNistObjectIdentifiers.IdSha3_384);
     Foids.Add('SHA3-512', TNistObjectIdentifiers.IdSha3_512);
+    Foids.Add('SHAKE128', TNistObjectIdentifiers.IdShake128);
+    Foids.Add('SHAKE256', TNistObjectIdentifiers.IdShake256);
     Foids.Add('RIPEMD128', TTeleTrusTObjectIdentifiers.RIPEMD128);
     Foids.Add('RIPEMD160', TTeleTrusTObjectIdentifiers.RIPEMD160);
     Foids.Add('RIPEMD256', TTeleTrusTObjectIdentifiers.RIPEMD256);

+ 13 - 5
CryptoLib/src/Security/ClpGeneratorUtilities.pas

@@ -225,6 +225,12 @@ begin
   AddHMacKeyGenerator('SHA512/224', []);
   AddHMacKeyGenerator('SHA512/256', []);
 
+  AddHMacKeyGenerator('KECCAK224', []);
+  AddHMacKeyGenerator('KECCAK256', []);
+  AddHMacKeyGenerator('KECCAK288', []);
+  AddHMacKeyGenerator('KECCAK384', []);
+  AddHMacKeyGenerator('KECCAK512', []);
+
   AddHMacKeyGenerator('SHA3-224',
     [TNistObjectIdentifiers.IdHMacWithSha3_224.ID]);
   AddHMacKeyGenerator('SHA3-256',
@@ -258,19 +264,21 @@ begin
   AddKpgAlgorithm('Ed25519', ['Ed25519ctx', 'Ed25519ph',
     TEdECObjectIdentifiers.id_Ed25519.ID]);
   AddKpgAlgorithm('Ed25519Blake2B', ['Ed25519Blake2Bctx', 'Ed25519Blake2Bph']);
-  AddKpgAlgorithm('X25519', TEdECObjectIdentifiers.id_X25519.ID);
+  AddKpgAlgorithm('X25519', [TEdECObjectIdentifiers.id_X25519.ID]);
 
   AddDefaultKeySizeEntries(128, ['AES128', 'BLOWFISH', 'HMACMD2', 'HMACMD4',
     'HMACMD5', 'HMACRIPEMD128', 'SALSA20']);
   AddDefaultKeySizeEntries(160, ['HMACRIPEMD160', 'HMACSHA1']);
   AddDefaultKeySizeEntries(192, ['AES', 'AES192', 'HMACTIGER']);
-  AddDefaultKeySizeEntries(224, ['HMACSHA3-224', 'HMACSHA224',
+  AddDefaultKeySizeEntries(224, ['HMACSHA3-224', 'HMACKECCAK224', 'HMACSHA224',
     'HMACSHA512/224']);
   AddDefaultKeySizeEntries(256, ['AES256', 'HMACGOST3411-2012-256',
-    'HMACSHA3-256', 'HMACSHA256', 'HMACSHA512/256']);
-  AddDefaultKeySizeEntries(384, ['HMACSHA3-384', 'HMACSHA384']);
+    'HMACSHA3-256', 'HMACKECCAK256', 'HMACSHA256', 'HMACSHA512/256']);
+  AddDefaultKeySizeEntries(288, ['HMACKECCAK288']);
+  AddDefaultKeySizeEntries(384, ['HMACSHA3-384', 'HMACKECCAK384',
+    'HMACSHA384']);
   AddDefaultKeySizeEntries(512, ['HMACGOST3411-2012-512', 'HMACSHA3-512',
-    'HMACSHA512']);
+    'HMACKECCAK512', 'HMACSHA512']);
 end;
 
 class constructor TGeneratorUtilities.CreateGeneratorUtilities;

+ 1 - 1
CryptoLib/src/Security/ClpMacUtilities.pas

@@ -37,7 +37,7 @@ uses
   ClpCryptoLibTypes;
 
 resourcestring
-  SUnRecognizedMac = '"Mac " %s not recognised.';
+  SUnRecognizedMac = 'Mac "%s" not recognised.';
 
 type
   TMacUtilities = class sealed(TObject)

+ 4 - 1
CryptoLib/src/Security/ClpParameterUtilities.pas

@@ -111,7 +111,7 @@ end;
 class procedure TParameterUtilities.Boot;
 begin
   Falgorithms := TDictionary<String, String>.Create();
-  FbasicIVSizes := TDictionary<string, Integer>.Create();
+  FbasicIVSizes := TDictionary<string, Int32>.Create();
 
   TNistObjectIdentifiers.Boot;
 
@@ -131,8 +131,11 @@ begin
     TNistObjectIdentifiers.IdAes256Cfb.ID,
     TNistObjectIdentifiers.IdAes256Ecb.ID,
     TNistObjectIdentifiers.IdAes256Ofb.ID]);
+  AddAlgorithm('BLOWFISH', ['1.3.6.1.4.1.3029.1.2']);
+  AddAlgorithm('RIJNDAEL', []);
   AddAlgorithm('SALSA20', []);
 
+  AddBasicIVSizeEntries(8, ['BLOWFISH']);
   AddBasicIVSizeEntries(16, ['AES', 'AES128', 'AES192', 'AES256']);
 
 end;

+ 69 - 0
CryptoLib/src/Security/ClpSignerUtilities.pas

@@ -36,12 +36,25 @@ uses
   ClpOiwObjectIdentifiers,
   ClpNistObjectIdentifiers,
   ClpCryptoProObjectIdentifiers,
+  ClpEdECObjectIdentifiers,
   ClpParameterUtilities,
   ClpIAsymmetricKeyParameter,
   ClpDsaSigner,
   ClpIDsaSigner,
   ClpECDsaSigner,
   ClpIECDsaSigner,
+  ClpEd25519Signer,
+  ClpIEd25519Signer,
+  ClpEd25519CtxSigner,
+  ClpIEd25519CtxSigner,
+  ClpEd25519PhSigner,
+  ClpIEd25519PhSigner,
+  ClpEd25519Blake2BSigner,
+  ClpIEd25519Blake2BSigner,
+  ClpEd25519CtxBlake2BSigner,
+  ClpIEd25519CtxBlake2BSigner,
+  ClpEd25519PhBlake2BSigner,
+  ClpIEd25519PhBlake2BSigner,
   ClpISigner,
   ClpISecureRandom,
   ClpIAsn1Objects,
@@ -126,6 +139,7 @@ begin
   TCryptoProObjectIdentifiers.Boot;
   TEacObjectIdentifiers.Boot;
   TBsiObjectIdentifiers.Boot;
+  TEdECObjectIdentifiers.Boot;
 
   Falgorithms.Add('NONEWITHDSA', 'NONEwithDSA');
   Falgorithms.Add('DSAWITHNONE', 'NONEwithDSA');
@@ -340,6 +354,17 @@ begin
   // Falgorithms.Add(TCryptoProObjectIdentifiers.GostR3411x94WithGostR3410x2001.id,
   // 'ECGOST3410');
 
+  // ED25519
+  Falgorithms.Add('ED25519', 'Ed25519');
+  Falgorithms.Add(TEdECObjectIdentifiers.id_Ed25519.id, 'Ed25519');
+  Falgorithms.Add('ED25519CTX', 'Ed25519ctx');
+  Falgorithms.Add('ED25519PH', 'Ed25519ph');
+
+  // ED25519Blake2B
+  Falgorithms.Add('ED25519BLAKE2B', 'Ed25519Blake2B');
+  Falgorithms.Add('ED25519BLAKE2BCTX', 'Ed25519Blake2Bctx');
+  Falgorithms.Add('ED25519BLAKE2BPH', 'Ed25519Blake2Bph');
+
   // ECSCHNORR SIPA
 
   Falgorithms.Add('SHA1/ECSCHNORR/SIPA', 'SHA-1withECSCHNORRSIPA');
@@ -409,6 +434,8 @@ begin
   //
   // Foids.Add('ECGOST3410',
   // TCryptoProObjectIdentifiers.GostR3411x94WithGostR3410x2001);
+
+  Foids.Add('Ed25519', TEdECObjectIdentifiers.id_Ed25519);
 end;
 
 class constructor TSignerUtilities.CreateSignerUtilities;
@@ -475,6 +502,48 @@ begin
     mechanism := algorithm;
   end;
 
+  if (TStringUtils.BeginsWith(mechanism, 'Ed25519', True)) then
+  begin
+    if TStringUtils.EndsWith(mechanism, 'Blake2B', True) then
+    begin
+      if (mechanism = 'Ed25519Blake2B') then
+      begin
+        Result := TEd25519Blake2BSigner.Create() as IEd25519Blake2BSigner;
+        Exit;
+      end;
+      if (mechanism = 'Ed25519ctxBlake2B') then
+      begin
+        Result := TEd25519ctxBlake2BSigner.Create(Nil)
+          as IEd25519ctxBlake2BSigner;
+        Exit;
+      end;
+      if (mechanism = 'Ed25519phBlake2B') then
+      begin
+        Result := TEd25519phBlake2BSigner.Create(Nil)
+          as IEd25519phBlake2BSigner;
+        Exit;
+      end;
+    end
+    else
+    begin
+      if (mechanism = 'Ed25519') then
+      begin
+        Result := TEd25519Signer.Create() as IEd25519Signer;
+        Exit;
+      end;
+      if (mechanism = 'Ed25519ctx') then
+      begin
+        Result := TEd25519ctxSigner.Create(Nil) as IEd25519ctxSigner;
+        Exit;
+      end;
+      if (mechanism = 'Ed25519ph') then
+      begin
+        Result := TEd25519phSigner.Create(Nil) as IEd25519phSigner;
+        Exit;
+      end;
+    end;
+  end;
+
   if TStringUtils.EndsWith(mechanism, 'withDSA', True) then
   begin
     DigestName := System.Copy(mechanism, 1, TStringUtils.LastIndexOf(mechanism,

+ 46 - 10
CryptoLib/src/Utils/ClpArrayUtils.pas

@@ -74,6 +74,9 @@ type
     class function Prepend(const A: TCryptoLibByteArray; B: Byte)
       : TCryptoLibByteArray; static;
 
+    class function Append(const A: TCryptoLibByteArray; B: Byte)
+      : TCryptoLibByteArray; static;
+
     class function CopyOf(const data: TCryptoLibByteArray; newLength: Int32)
       : TCryptoLibByteArray; static;
 
@@ -92,6 +95,8 @@ type
     class procedure Fill(const buf: TCryptoLibUInt32Array; from, &to: Int32;
       filler: UInt32); overload; static;
 
+    class procedure ZeroFill(const buf: TCryptoLibByteArray); static;
+
   end;
 
 implementation
@@ -252,31 +257,45 @@ end;
 class procedure TArrayUtils.Fill(const buf: TCryptoLibByteArray;
   from, &to: Int32; filler: Byte);
 begin
-  System.FillChar(buf[from], (&to - from) * System.SizeOf(Byte), filler);
+  if buf <> Nil then
+  begin
+    System.FillChar(buf[from], (&to - from) * System.SizeOf(Byte), filler);
+  end;
 end;
 
 class procedure TArrayUtils.Fill(const buf: TCryptoLibInt32Array;
   from, &to: Int32; filler: Int32);
 begin
-  while from < &to do
+  if buf <> Nil then
   begin
-    buf[from] := filler;
-    System.Inc(from);
+    while from < &to do
+    begin
+      buf[from] := filler;
+      System.Inc(from);
+    end;
   end;
 end;
 
 class procedure TArrayUtils.Fill(const buf: TCryptoLibUInt32Array;
   from, &to: Int32; filler: UInt32);
 begin
+  if buf <> Nil then
+  begin
 {$IFDEF FPC}
-  System.FillDWord(buf[from], (&to - from), filler);
+    System.FillDWord(buf[from], (&to - from), filler);
 {$ELSE}
-  while from < &to do
-  begin
-    buf[from] := filler;
-    System.Inc(from);
-  end;
+    while from < &to do
+    begin
+      buf[from] := filler;
+      System.Inc(from);
+    end;
 {$ENDIF}
+  end;
+end;
+
+class procedure TArrayUtils.ZeroFill(const buf: TCryptoLibByteArray);
+begin
+  TArrayUtils.Fill(buf, 0, System.Length(buf), Byte(0));
 end;
 
 class function TArrayUtils.GetArrayHashCode(const data
@@ -420,4 +439,21 @@ begin
   Result[0] := B;
 end;
 
+class function TArrayUtils.Append(const A: TCryptoLibByteArray; B: Byte)
+  : TCryptoLibByteArray;
+var
+  &length: Int32;
+begin
+  if (A = Nil) then
+  begin
+    Result := TCryptoLibByteArray.Create(B);
+    Exit;
+  end;
+
+  Length := System.Length(A);
+  System.SetLength(Result, Length + 1);
+  System.Move(A[0], Result[0], Length * System.SizeOf(Byte));
+  Result[Length] := B;
+end;
+
 end.

+ 0 - 2
CryptoLib/src/Utils/ClpCryptoLibTypes.pas

@@ -222,8 +222,6 @@ type
   TCryptoLibCustomByteArrayBuffer = TCryptoLibCustomArrayBuffer<Byte>;
 
 const
-  EmptyBytesNotNil: TCryptoLibCustomByteArrayBuffer = (FData: Nil; FLength: 0;
-    FIsNil: False);
   EmptyBytesNil: TCryptoLibCustomByteArrayBuffer = (FData: Nil; FLength: 0;
     FIsNil: True);
 

+ 5 - 6
CryptoLib/src/Utils/Randoms/ClpPcgRandomMinimal.pas

@@ -145,7 +145,7 @@ type
     /// <param name="minimum">The minimum inclusive value.</param>
     /// <param name="exclusiveBound">The maximum exclusive bound.</param>
 
-    class function NextUInt32(minimum: UInt32; exclusiveBound: UInt32): UInt32;
+    class function NextUInt32(minimum, exclusiveBound: UInt32): UInt32;
       overload; inline;
 
     /// <summary>
@@ -155,8 +155,7 @@ type
     /// <param name="minimum">The minimum inclusive value.</param>
     /// <param name="exclusiveBound">The maximum exclusive bound.</param>
 
-    class function NextInt(minimum: Integer; exclusiveBound: Integer)
-      : Integer; inline;
+    class function NextInt(minimum, exclusiveBound: Int32): Int32; inline;
 
   end;
 
@@ -275,18 +274,18 @@ begin
   Seed(LinitState, LinitSeq);
 end;
 
-constructor TPcg.Create(initState: UInt64; initSeq: UInt64);
+constructor TPcg.Create(initState, initSeq: UInt64);
 begin
   Seed(initState, initSeq);
 end;
 
-class function TPcg.NextInt(minimum: Integer; exclusiveBound: Integer): Integer;
+class function TPcg.NextInt(minimum, exclusiveBound: Int32): Int32;
 var
   boundRange, rangeResult: UInt32;
 begin
   boundRange := UInt32(exclusiveBound - minimum);
   rangeResult := Range32(boundRange);
-  result := Integer(rangeResult) + Integer(minimum);
+  result := Int32(rangeResult) + Int32(minimum);
 end;
 
 end.