summary refs log tree commit diff
diff options
context:
space:
mode:
authorPeter Dettman <peter.dettman@gmail.com>2022-10-18 16:02:29 +0700
committerPeter Dettman <peter.dettman@gmail.com>2022-10-18 16:02:29 +0700
commitfe8f738e093eede32b55b329a6a864eb680dc281 (patch)
tree67b5abd12be56c6a6887133c8211d5ea9863d229
parentReplace LinearAlgebra with BikePolynomial (diff)
downloadBouncyCastle.NET-ed25519-fe8f738e093eede32b55b329a6a864eb680dc281.tar.xz
Refactoring in Pqc.Crypto.Bike (performance)
-rw-r--r--crypto/src/pqc/crypto/bike/BikeEngine.cs120
-rw-r--r--crypto/src/pqc/crypto/bike/BikeKemExtractor.cs23
-rw-r--r--crypto/src/pqc/crypto/bike/BikeKemGenerator.cs29
-rw-r--r--crypto/src/pqc/crypto/bike/BikeKeyGenerationParameters.cs17
-rw-r--r--crypto/src/pqc/crypto/bike/BikeKeyPairGenerator.cs21
-rw-r--r--crypto/src/pqc/crypto/bike/BikeKeyParameters.cs17
-rw-r--r--crypto/src/pqc/crypto/bike/BikeParameters.cs47
-rw-r--r--crypto/src/pqc/crypto/bike/BikePolynomial.cs168
-rw-r--r--crypto/src/pqc/crypto/bike/BikePrivateKeyParameters.cs11
-rw-r--r--crypto/src/pqc/crypto/bike/BikePublicKeyParameters.cs16
-rw-r--r--crypto/src/pqc/crypto/bike/BikeRandomGenerator.cs64
-rw-r--r--crypto/src/pqc/crypto/bike/BikeUtilities.cs (renamed from crypto/src/pqc/crypto/bike/Utils.cs)37
-rw-r--r--crypto/test/src/pqc/crypto/test/BikeVectorTest.cs10
13 files changed, 206 insertions, 374 deletions
diff --git a/crypto/src/pqc/crypto/bike/BikeEngine.cs b/crypto/src/pqc/crypto/bike/BikeEngine.cs
index ecd7d7efe..a872c68a7 100644
--- a/crypto/src/pqc/crypto/bike/BikeEngine.cs
+++ b/crypto/src/pqc/crypto/bike/BikeEngine.cs
@@ -7,7 +7,7 @@ using Org.BouncyCastle.Utilities;
 
 namespace Org.BouncyCastle.Pqc.Crypto.Bike
 {
-    public class BikeEngine
+    internal sealed class BikeEngine
     {
         // degree of R
         private int r;
@@ -34,7 +34,7 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
         private int L_BYTE;
         private int R_BYTE;
 
-        public BikeEngine(int r, int w, int t, int l, int nbIter, int tau)
+        internal BikeEngine(int r, int w, int t, int l, int nbIter, int tau)
         {
             this.r = r;
             this.w = w;
@@ -50,17 +50,13 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
             this.reductionPoly = new BikePolynomial(r);
         }
 
-        public int GetSessionKeySize()
-        {
-            return L_BYTE;
-        }
+        internal int SessionKeySize => L_BYTE;
 
         private byte[] FunctionH(byte[] seed)
         {
             IXof digest = new ShakeDigest(256);
             digest.BlockUpdate(seed, 0, seed.Length);
-            byte[] wlist = BikeRandomGenerator.GenerateRandomByteArray(r * 2, 2 * R_BYTE, t, digest);
-            return wlist;
+            return BikeUtilities.GenerateRandomByteArray(r * 2, 2 * R_BYTE, t, digest);
         }
 
         private byte[] FunctionL(byte[] e0, byte[] e1)
@@ -68,7 +64,6 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
             byte[] hashRes = new byte[48];
             byte[] res = new byte[L_BYTE];
 
-            
             Sha3Digest digest = new Sha3Digest(384);
             digest.BlockUpdate(e0, 0, e0.Length);
             digest.BlockUpdate(e1, 0, e1.Length);
@@ -103,9 +98,9 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
          * @param h             h
          * @param random        Secure Random
          **/
-        public void GenKeyPair(byte[] h0, byte[] h1, byte[] sigma, byte[] h, SecureRandom random)
+        internal void GenKeyPair(byte[] h0, byte[] h1, byte[] sigma, byte[] h, SecureRandom random)
         {
-            //         Randomly generate seeds
+            // Randomly generate seeds
             byte[] seeds = new byte[64];
             random.NextBytes(seeds);
 
@@ -117,9 +112,9 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
             IXof digest = new ShakeDigest(256);
             digest.BlockUpdate(seed1, 0, seed1.Length);
 
-            //      1. Randomly generate h0, h1
-            byte[] h0Tmp = BikeRandomGenerator.GenerateRandomByteArray(r, R_BYTE, hw, digest);
-            byte[] h1Tmp = BikeRandomGenerator.GenerateRandomByteArray(r, R_BYTE, hw, digest);
+            // 1. Randomly generate h0, h1
+            byte[] h0Tmp = BikeUtilities.GenerateRandomByteArray(r, R_BYTE, hw, digest);
+            byte[] h1Tmp = BikeUtilities.GenerateRandomByteArray(r, R_BYTE, hw, digest);
 
             Array.Copy(h0Tmp, 0, h0, 0, h0.Length);
             Array.Copy(h1Tmp, 0, h1, 0, h1.Length);
@@ -127,12 +122,12 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
             byte[] h1Bits = new byte[r];
             byte[] h0Bits = new byte[r];
 
-            Utils.FromByteArrayToBitArray(h0Bits, h0Tmp);
-            Utils.FromByteArrayToBitArray(h1Bits, h1Tmp);
+            BikeUtilities.FromByteArrayToBitArray(h0Bits, h0Tmp);
+            BikeUtilities.FromByteArrayToBitArray(h1Bits, h1Tmp);
 
             // remove last 0 bits (most significant bits with 0 mean non-sense)
-            byte[] h0Cut = Utils.RemoveLast0Bits(h0Bits);
-            byte[] h1Cut = Utils.RemoveLast0Bits(h1Bits);
+            byte[] h0Cut = BikeUtilities.RemoveLast0Bits(h0Bits);
+            byte[] h1Cut = BikeUtilities.RemoveLast0Bits(h1Bits);
 
             // 2. Compute h
             BikePolynomial h0Poly = new BikePolynomial(h0Cut);
@@ -144,7 +139,7 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
             // Get coefficients of hPoly
             byte[] hTmp = hPoly.GetEncoded();
             byte[] hByte = new byte[R_BYTE];
-            Utils.FromBitArrayToByteArray(hByte, hTmp);
+            BikeUtilities.FromBitArrayToByteArray(hByte, hTmp);
             Array.Copy(hByte, 0, h, 0, h.Length);
 
             //3. Parse seed2 as sigma
@@ -161,7 +156,7 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
          * @param h             public key
          * @param random        Secure Random
          **/
-        public void Encaps(byte[] c0, byte[] c1, byte[] k, byte[] h, SecureRandom random)
+        internal void Encaps(byte[] c0, byte[] c1, byte[] k, byte[] h, SecureRandom random)
         {
             byte[] seeds = new byte[64];
             random.NextBytes(seeds);
@@ -174,14 +169,14 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
             byte[] eBytes = FunctionH(m);
 
             byte[] eBits = new byte[2 * r];
-            Utils.FromByteArrayToBitArray(eBits, eBytes);
+            BikeUtilities.FromByteArrayToBitArray(eBits, eBytes);
 
             byte[] e0Bits = Arrays.CopyOfRange(eBits, 0, r);
             byte[] e1Bits = Arrays.CopyOfRange(eBits, r, eBits.Length);
 
             // remove last 0 bits (most significant bits with 0 mean no sense)
-            byte[] e0Cut = Utils.RemoveLast0Bits(e0Bits);
-            byte[] e1Cut = Utils.RemoveLast0Bits(e1Bits);
+            byte[] e0Cut = BikeUtilities.RemoveLast0Bits(e0Bits);
+            byte[] e1Cut = BikeUtilities.RemoveLast0Bits(e1Bits);
 
             BikePolynomial e0 = new BikePolynomial(e0Cut);
             BikePolynomial e1 = new BikePolynomial(e1Cut);
@@ -189,23 +184,23 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
             // 3. Calculate c
             // calculate c0
             byte[] h0Bits = new byte[r];
-            Utils.FromByteArrayToBitArray(h0Bits, h);
-            BikePolynomial hPoly = new BikePolynomial(Utils.RemoveLast0Bits(h0Bits));
+            BikeUtilities.FromByteArrayToBitArray(h0Bits, h);
+            BikePolynomial hPoly = new BikePolynomial(BikeUtilities.RemoveLast0Bits(h0Bits));
             BikePolynomial c0Poly = e0.Add(e1.ModKaratsubaMultiplyBigDeg(hPoly, reductionPoly));
 
             byte[] c0Bits = c0Poly.GetEncoded();
             byte[] c0Bytes = new byte[R_BYTE];
-            Utils.FromBitArrayToByteArray(c0Bytes, c0Bits);
+            BikeUtilities.FromBitArrayToByteArray(c0Bytes, c0Bits);
             Array.Copy(c0Bytes, 0, c0, 0, c0.Length);
 
             //calculate c1
             byte[] e0Bytes = new byte[R_BYTE];
-            Utils.FromBitArrayToByteArray(e0Bytes, e0Bits);
+            BikeUtilities.FromBitArrayToByteArray(e0Bytes, e0Bits);
             byte[] e1Bytes = new byte[R_BYTE];
-            Utils.FromBitArrayToByteArray(e1Bytes, e1Bits);
+            BikeUtilities.FromBitArrayToByteArray(e1Bytes, e1Bits);
 
             byte[] tmp = FunctionL(e0Bytes, e1Bytes);
-            byte[] c1Tmp = Utils.XorBytes(m, tmp, L_BYTE);
+            byte[] c1Tmp = BikeUtilities.XorBytes(m, tmp, L_BYTE);
             Array.Copy(c1Tmp, 0, c1, 0, c1.Length);
 
             // 4. Calculate K
@@ -224,19 +219,19 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
          * @param c1            ciphertext
          * @param k             session key
          **/
-        public void Decaps(byte[] k, byte[] h0, byte[] h1, byte[] sigma, byte[] c0, byte[] c1)
+        internal void Decaps(byte[] k, byte[] h0, byte[] h1, byte[] sigma, byte[] c0, byte[] c1)
         {
             //convert to bits
             byte[] c0Bits = new byte[this.r];
             byte[] h0Bits = new byte[this.r];
             byte[] sigmaBits = new byte[this.l];
 
-            Utils.FromByteArrayToBitArray(c0Bits, c0);
-            Utils.FromByteArrayToBitArray(h0Bits, h0);
-            Utils.FromByteArrayToBitArray(sigmaBits, sigma);
+            BikeUtilities.FromByteArrayToBitArray(c0Bits, c0);
+            BikeUtilities.FromByteArrayToBitArray(h0Bits, h0);
+            BikeUtilities.FromByteArrayToBitArray(sigmaBits, sigma);
 
-            byte[] c0Cut = Utils.RemoveLast0Bits(c0Bits);
-            byte[] h0Cut = Utils.RemoveLast0Bits(h0Bits);
+            byte[] c0Cut = BikeUtilities.RemoveLast0Bits(c0Bits);
+            byte[] h0Cut = BikeUtilities.RemoveLast0Bits(h0Bits);
 
             // Get compact version of h0, h1
             int[] h0Compact = new int[hw];
@@ -250,18 +245,18 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
             // 1. Compute e'
             byte[] ePrimeBits = BGFDecoder(syndrome, h0Compact, h1Compact);
             byte[] ePrimeBytes = new byte[2 * R_BYTE];
-            Utils.FromBitArrayToByteArray(ePrimeBytes, ePrimeBits);
+            BikeUtilities.FromBitArrayToByteArray(ePrimeBytes, ePrimeBits);
 
             byte[] e0Bits = Arrays.CopyOfRange(ePrimeBits, 0, r);
             byte[] e1Bits = Arrays.CopyOfRange(ePrimeBits, r, ePrimeBits.Length);
 
             byte[] e0Bytes = new byte[R_BYTE];
-            Utils.FromBitArrayToByteArray(e0Bytes, e0Bits);
+            BikeUtilities.FromBitArrayToByteArray(e0Bytes, e0Bits);
             byte[] e1Bytes = new byte[R_BYTE];
-            Utils.FromBitArrayToByteArray(e1Bytes, e1Bits);
+            BikeUtilities.FromBitArrayToByteArray(e1Bytes, e1Bits);
 
             // 2. Compute m'
-            byte[] mPrime = Utils.XorBytes(c1, FunctionL(e0Bytes, e1Bytes), L_BYTE);
+            byte[] mPrime = BikeUtilities.XorBytes(c1, FunctionL(e0Bytes, e1Bytes), L_BYTE);
 
             // 3. Compute K
             byte[] tmpK = new byte[l];
@@ -300,7 +295,7 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
                 byte[] black = new byte[2 * r];
                 byte[] gray = new byte[2 * r];
 
-                int T = Threshold(Utils.GetHammingWeight(s), i, r);
+                int T = Threshold(BikeUtilities.GetHammingWeight(s), r);
 
                 BFIter(s, e, T, h0Compact, h1Compact, h0CompactCol, h1CompactCol, black, gray);
 
@@ -311,7 +306,7 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
                 }
             }
 
-            if (Utils.GetHammingWeight(s) == 0)
+            if (BikeUtilities.GetHammingWeight(s) == 0)
                 return e;
 
             return null;
@@ -319,7 +314,7 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
 
         private byte[] Transpose(byte[] input)
         {
-            byte[] tmp = Utils.Append0s(input, r); // append zeros to s
+            byte[] tmp = BikeUtilities.Append0s(input, r); // append zeros to s
             byte[] output = new byte[r];
             output[0] = tmp[0];
             for (int i = 1; i < r; i++)
@@ -329,7 +324,8 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
             return output;
         }
 
-        private void BFIter(byte[] s, byte[] e, int T, int[] h0Compact, int[] h1Compact, int[] h0CompactCol, int[] h1CompactCol, byte[] black, byte[] gray)
+        private void BFIter(byte[] s, byte[] e, int T, int[] h0Compact, int[] h1Compact, int[] h0CompactCol,
+            int[] h1CompactCol, byte[] black, byte[] gray)
         {
             int[] updatedIndices = new int[2 * r];
 
@@ -405,28 +401,28 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
             }
         }
 
-        private int Threshold(int hammingWeight, int i, int r)
+        private int Threshold(int hammingWeight, int r)
         {
-            double d = 0;
-            int floorD = 0;
+            double d;
+            int floorD;
             int res = 0;
             switch (r)
             {
-                case 12323:
-                    d = 0.0069722 * hammingWeight + 13.530;
-                    floorD = (int) System.Math.Floor(d);
-                    res = floorD > 36 ? floorD : 36;
-                    break;
-                case 24659:
-                    d = 0.005265 * hammingWeight + 15.2588;
-                    floorD = (int) System.Math.Floor(d);
-                    res = floorD > 52 ? floorD : 52;
-                    break;
-                case 40973:
-                    d = 0.00402312 * hammingWeight + 17.8785;
-                    floorD = (int) System.Math.Floor(d);
-                    res = floorD > 69 ? floorD : 69;
-                    break;
+            case 12323:
+                d = 0.0069722 * hammingWeight + 13.530;
+                floorD = (int) System.Math.Floor(d);
+                res = floorD > 36 ? floorD : 36;
+                break;
+            case 24659:
+                d = 0.005265 * hammingWeight + 15.2588;
+                floorD = (int) System.Math.Floor(d);
+                res = floorD > 52 ? floorD : 52;
+                break;
+            case 40973:
+                d = 0.00402312 * hammingWeight + 17.8785;
+                floorD = (int) System.Math.Floor(d);
+                res = floorD > 69 ? floorD : 69;
+                break;
             }
             return res;
         }
@@ -454,9 +450,7 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
                 for (int j = 0; j < 8; j++)
                 {
                     if ((i * 8 + j) == this.r)
-                    {
                         break;
-                    }
 
                     if (((h[i] >> j) & 1) == 1)
                     {
diff --git a/crypto/src/pqc/crypto/bike/BikeKemExtractor.cs b/crypto/src/pqc/crypto/bike/BikeKemExtractor.cs
index bcc0c124c..b6358e3d2 100644
--- a/crypto/src/pqc/crypto/bike/BikeKemExtractor.cs
+++ b/crypto/src/pqc/crypto/bike/BikeKemExtractor.cs
@@ -1,4 +1,5 @@
 using Org.BouncyCastle.Crypto;
+using Org.BouncyCastle.Pqc.Crypto.Sike;
 using Org.BouncyCastle.Utilities;
 using System;
 using System.Collections.Generic;
@@ -6,28 +7,23 @@ using System.Text;
 
 namespace Org.BouncyCastle.Pqc.Crypto.Bike
 {
-    public class BikeKemExtractor : IEncapsulatedSecretExtractor
+    public sealed class BikeKemExtractor
+        : IEncapsulatedSecretExtractor
     {
-        private BikeEngine engine;
-
-        private BikeKeyParameters key;
-        private int defaultKeySize; 
+        private readonly BikeKeyParameters key;
 
         public BikeKemExtractor(BikePrivateKeyParameters privParams)
         {
             this.key = privParams;
-            initCipher(key.Parameters);
-        }
-
-        private void initCipher(BikeParameters param)
-        {
-            engine = param.BIKEEngine;
-            defaultKeySize = param.DefaultKeySize;
         }
 
         public byte[] ExtractSecret(byte[] encapsulation)
         {
-            byte[] session_key = new byte[engine.GetSessionKeySize()];
+            BikeParameters parameters = key.Parameters;
+            BikeEngine engine = parameters.BikeEngine;
+            int defaultKeySize = parameters.DefaultKeySize;
+
+            byte[] session_key = new byte[engine.SessionKeySize];
             BikePrivateKeyParameters secretKey = (BikePrivateKeyParameters)key;
 
             // Extract c0, c1 from encapsulation c
@@ -43,6 +39,5 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
         }
 
         public int EncapsulationLength => key.Parameters.RByte + key.Parameters.LByte;
-
     }
 }
diff --git a/crypto/src/pqc/crypto/bike/BikeKemGenerator.cs b/crypto/src/pqc/crypto/bike/BikeKemGenerator.cs
index 461cdae97..da4221967 100644
--- a/crypto/src/pqc/crypto/bike/BikeKemGenerator.cs
+++ b/crypto/src/pqc/crypto/bike/BikeKemGenerator.cs
@@ -1,15 +1,16 @@
-using Org.BouncyCastle.Crypto;
+using System;
+
+using Org.BouncyCastle.Crypto;
 using Org.BouncyCastle.Security;
 using Org.BouncyCastle.Utilities;
-using System;
-using System.Collections.Generic;
-using System.Text;
 
 namespace Org.BouncyCastle.Pqc.Crypto.Bike
 {
-    public class BikeKemGenerator : IEncapsulatedSecretGenerator
+    public sealed class BikeKemGenerator
+        : IEncapsulatedSecretGenerator
     {
-        private SecureRandom sr;
+        private readonly SecureRandom sr;
+
         public BikeKemGenerator(SecureRandom random)
         {
             this.sr = random;
@@ -18,21 +19,23 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
         public ISecretWithEncapsulation GenerateEncapsulated(AsymmetricKeyParameter recipientKey)
         {
             BikePublicKeyParameters key = (BikePublicKeyParameters)recipientKey;
-            BikeEngine engine = key.Parameters.BIKEEngine;
+            BikeParameters parameters = key.Parameters;
+            BikeEngine engine = parameters.BikeEngine;
 
-            byte[] K = new byte[key.Parameters.LByte];
-            byte[] c0 = new byte[key.Parameters.RByte];
-            byte[] c1 = new byte[key.Parameters.LByte];
+            byte[] K = new byte[parameters.LByte];
+            byte[] c0 = new byte[parameters.RByte];
+            byte[] c1 = new byte[parameters.LByte];
             byte[] h = key.PublicKey;
 
             engine.Encaps(c0, c1, K, h, sr);
 
             byte[] cipherText = Arrays.Concatenate(c0, c1);
 
-            return new SecretWithEncapsulationImpl(Arrays.CopyOfRange(K, 0, key.Parameters.DefaultKeySize / 8), cipherText);
+            return new SecretWithEncapsulationImpl(Arrays.CopyOfRange(K, 0, parameters.DefaultKeySize / 8), cipherText);
         }
 
-        private class SecretWithEncapsulationImpl : ISecretWithEncapsulation
+        private class SecretWithEncapsulationImpl
+            : ISecretWithEncapsulation
         {
             private volatile bool hasBeenDestroyed = false;
 
@@ -76,9 +79,7 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
             void CheckDestroyed()
             {
                 if (IsDestroyed())
-                {
                     throw new Exception("data has been destroyed");
-                }
             }
         }
     }
diff --git a/crypto/src/pqc/crypto/bike/BikeKeyGenerationParameters.cs b/crypto/src/pqc/crypto/bike/BikeKeyGenerationParameters.cs
index 226d939fc..397c7bcdb 100644
--- a/crypto/src/pqc/crypto/bike/BikeKeyGenerationParameters.cs
+++ b/crypto/src/pqc/crypto/bike/BikeKeyGenerationParameters.cs
@@ -1,22 +1,19 @@
 using Org.BouncyCastle.Crypto;
 using Org.BouncyCastle.Security;
-using System;
-using System.Collections.Generic;
-using System.Text;
 
 namespace Org.BouncyCastle.Pqc.Crypto.Bike
 {
-    public class BikeKeyGenerationParameters : KeyGenerationParameters
+    public sealed class BikeKeyGenerationParameters
+        : KeyGenerationParameters
     {
-        private BikeParameters param;
+        private readonly BikeParameters m_parameters;
 
-        public BikeKeyGenerationParameters(
-                SecureRandom random,
-                BikeParameters param) : base(random, 256)
+        public BikeKeyGenerationParameters(SecureRandom random, BikeParameters parameters)
+            : base(random, 256)
         {
-            this.param = param;
+            m_parameters = parameters;
         }
 
-        public BikeParameters Parameters => param;
+        public BikeParameters Parameters => m_parameters;
     }
 }
diff --git a/crypto/src/pqc/crypto/bike/BikeKeyPairGenerator.cs b/crypto/src/pqc/crypto/bike/BikeKeyPairGenerator.cs
index f1b786336..5636458fd 100644
--- a/crypto/src/pqc/crypto/bike/BikeKeyPairGenerator.cs
+++ b/crypto/src/pqc/crypto/bike/BikeKeyPairGenerator.cs
@@ -1,12 +1,10 @@
 using Org.BouncyCastle.Crypto;
 using Org.BouncyCastle.Security;
-using System;
-using System.Collections.Generic;
-using System.Text;
 
 namespace Org.BouncyCastle.Pqc.Crypto.Bike
 {
-    public class BikeKeyPairGenerator : IAsymmetricCipherKeyPairGenerator
+    public sealed class BikeKeyPairGenerator
+        : IAsymmetricCipherKeyPairGenerator
     {
         private SecureRandom random;
 
@@ -34,6 +32,7 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
         private int R_BYTE;
 
         private BikeKeyGenerationParameters bikeKeyGenerationParameters;
+
         public void Init(KeyGenerationParameters param)
         {
             this.bikeKeyGenerationParameters = (BikeKeyGenerationParameters)param;
@@ -51,9 +50,10 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
             this.R_BYTE = (r + 7) / 8;
         }
 
-        private AsymmetricCipherKeyPair GenKeyPair()
+        public AsymmetricCipherKeyPair GenerateKeyPair()
         {
-            BikeEngine engine = bikeKeyGenerationParameters.Parameters.BIKEEngine;
+            BikeParameters parameters = bikeKeyGenerationParameters.Parameters;
+            BikeEngine engine = parameters.BikeEngine;
             byte[] h0 = new byte[R_BYTE];
             byte[] h1 = new byte[R_BYTE];
             byte[] h = new byte[R_BYTE];
@@ -62,15 +62,10 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
             engine.GenKeyPair(h0, h1, sigma, h, random);
 
             // form keys
-            BikePublicKeyParameters publicKey = new BikePublicKeyParameters(bikeKeyGenerationParameters.Parameters, h);
-            BikePrivateKeyParameters privateKey = new BikePrivateKeyParameters(bikeKeyGenerationParameters.Parameters, h0, h1, sigma);
+            BikePublicKeyParameters publicKey = new BikePublicKeyParameters(parameters, h);
+            BikePrivateKeyParameters privateKey = new BikePrivateKeyParameters(parameters, h0, h1, sigma);
 
             return new AsymmetricCipherKeyPair(publicKey, privateKey);
         }
-
-        public AsymmetricCipherKeyPair GenerateKeyPair()
-        {
-            return GenKeyPair();
-        }
     }
 }
diff --git a/crypto/src/pqc/crypto/bike/BikeKeyParameters.cs b/crypto/src/pqc/crypto/bike/BikeKeyParameters.cs
index 0ee8279a9..fd15138e4 100644
--- a/crypto/src/pqc/crypto/bike/BikeKeyParameters.cs
+++ b/crypto/src/pqc/crypto/bike/BikeKeyParameters.cs
@@ -1,21 +1,18 @@
 using Org.BouncyCastle.Crypto;
-using System;
-using System.Collections.Generic;
-using System.Text;
 
 namespace Org.BouncyCastle.Pqc.Crypto.Bike
 {
-    public class BikeKeyParameters : AsymmetricKeyParameter
+    public abstract class BikeKeyParameters
+        : AsymmetricKeyParameter
     {
-        private BikeParameters param;
+        private readonly BikeParameters m_parameters;
 
-        public BikeKeyParameters(
-                bool isPrivate,
-                BikeParameters param) : base(isPrivate)
+        public BikeKeyParameters(bool isPrivate, BikeParameters parameters)
+            : base(isPrivate)
         {
-            this.param = param;
+            this.m_parameters = parameters;
         }
 
-        public BikeParameters Parameters => param;
+        public BikeParameters Parameters => m_parameters;
     }
 }
diff --git a/crypto/src/pqc/crypto/bike/BikeParameters.cs b/crypto/src/pqc/crypto/bike/BikeParameters.cs
index e4d06b861..9fd658e0c 100644
--- a/crypto/src/pqc/crypto/bike/BikeParameters.cs
+++ b/crypto/src/pqc/crypto/bike/BikeParameters.cs
@@ -1,31 +1,29 @@
-using System;
-
-using Org.BouncyCastle.Crypto;
+using Org.BouncyCastle.Crypto;
 
 namespace Org.BouncyCastle.Pqc.Crypto.Bike
 {
-    public class BikeParameters
+    public sealed class BikeParameters
         : ICipherParameters
     {
         // 128 bits security
         public static BikeParameters bike128 = new BikeParameters("bike128", 12323, 142, 134, 256, 5, 3, 128);
 
         // 192 bits security
-        public static BikeParameters bike192 = new BikeParameters("bike192",24659, 206, 199, 256, 5, 3, 192);
+        public static BikeParameters bike192 = new BikeParameters("bike192", 24659, 206, 199, 256, 5, 3, 192);
 
         // 256 bits security
-        public static BikeParameters bike256 = new BikeParameters("bike256",40973, 274, 264, 256, 5, 3, 256);
-
-        private String name;
-        private int r;
-        private int w;
-        private int t;
-        private int l;
-        private int nbIter;
-        private int tau;
-        private int defaultKeySize;
+        public static BikeParameters bike256 = new BikeParameters("bike256", 40973, 274, 264, 256, 5, 3, 256);
+
+        private readonly string name;
+        private readonly int r;
+        private readonly int w;
+        private readonly int t;
+        private readonly int l;
+        private readonly int nbIter;
+        private readonly int tau;
+        private readonly int defaultKeySize;
+        private readonly BikeEngine bikeEngine;
 
-        private BikeEngine bikeEngine;
         internal BikeParameters(string name, int r, int w, int t, int l, int nbIter, int tau, int defaultKeySize)
         {
             this.name = name;
@@ -39,19 +37,6 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
             this.bikeEngine = new BikeEngine(r, w, t, l, nbIter, tau);
         }
 
-        internal BikeParameters(BikeParameters param)
-        {
-            this.name = param.name;
-            this.r = param.r;
-            this.w = param.w;
-            this.t = param.t;
-            this.l = param.l;
-            this.nbIter = param.nbIter;
-            this.tau = param.tau;
-            this.defaultKeySize = param.defaultKeySize;
-            this.bikeEngine = new BikeEngine(r, w, t, l, nbIter, tau);
-        }
-
         public int R => r;
         public int RByte => (r + 7) / 8;
         public int LByte => l / 8; 
@@ -60,8 +45,8 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
         public int L => l;
         public int NbIter => nbIter;
         public int Tau => tau;
-        public String Name => name;
+        public string Name => name;
         public int DefaultKeySize => defaultKeySize;
-        internal BikeEngine BIKEEngine => bikeEngine;
+        internal BikeEngine BikeEngine => bikeEngine;
     }
 }
diff --git a/crypto/src/pqc/crypto/bike/BikePolynomial.cs b/crypto/src/pqc/crypto/bike/BikePolynomial.cs
index 0d66fe433..eea34d838 100644
--- a/crypto/src/pqc/crypto/bike/BikePolynomial.cs
+++ b/crypto/src/pqc/crypto/bike/BikePolynomial.cs
@@ -23,7 +23,7 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
          */
         internal BikePolynomial(int degree)
         {
-            // Initial value (X^r + 1)
+            // Initial value (X^degree + 1)
             this.m_coefficients = new int[degree + 1];
             this.m_coefficients[degree] = 1;
             this.m_coefficients[0] ^= 1;
@@ -38,7 +38,7 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
          */
         private BikePolynomial(int[] coeffs)
         {
-            this.m_coefficients = NormalForm(coeffs);
+            this.m_coefficients = coeffs;
         }
 
         /**
@@ -87,7 +87,7 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
         internal BikePolynomial Add(BikePolynomial addend)
         {
             int[] resultCoeff = Add(m_coefficients, addend.m_coefficients);
-            return new BikePolynomial(resultCoeff);
+            return new BikePolynomial(NormalForm(resultCoeff));
         }
 
         /**
@@ -98,7 +98,7 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
          * @param b the second polynomial
          * @return a + b
          */
-        private int[] Add(int[] a, int[] b)
+        private static int[] Add(int[] a, int[] b)
         {
             int[] result, addend;
             if (a.Length < b.Length)
@@ -122,35 +122,12 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
             return result;
         }
 
-        /**
-         * Compute the product of a polynomial a with an element from the finite
-         * field <tt>GF(2^m)</tt>.
-         *
-         * @param a       the polynomial
-         * @param element an element of the finite field GF(2^m)
-         * @return <tt>a * element</tt>
-         */
-        private int[] MultWithElement(int[] a, int element)
+        private static void AddAt(int[] x, int[] z, int zPos)
         {
-            return element == 0 ? new int[1] : Arrays.Clone(a);
-        }
-
-        /**
-         * Compute the product of a polynomial with a monomial X^k.
-         *
-         * @param a the polynomial
-         * @param k the degree of the monomial
-         * @return <tt>a * X^k</tt>
-         */
-        private static int[] MultWithMonomial(int[] a, int k)
-        {
-            int d = ComputeDegree(a);
-            if (d == -1)
-                return new int[1];
-
-            int[] result = new int[k + d + 1];
-            Array.Copy(a, 0, result, k, d + 1);
-            return result;
+            for (int i = 0; i < x.Length; ++i)
+            {
+                z[zPos + i] ^= x[i];
+            }
         }
 
         /**
@@ -161,7 +138,7 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
          * @param f the second polynomial
          * @return int[][] {q,r}, where a = q*f+r and deg(r) &lt; deg(f);
          */
-        private int[][] Div(int[] a, int[] f)
+        private static int[][] Div(int[] a, int[] f)
         {
             int df = ComputeDegree(f);
             if (df == -1)
@@ -169,93 +146,17 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
 
             int degreeR1 = ComputeDegree(a);
             int[][] result = new int[2][];
-            result[0] = new int[1]{ 0 };
+            result[0] = new int[System.Math.Max(0, degreeR1 - df) + 1];
             result[1] = Arrays.CopyOf(a, degreeR1 + 1);
 
             while (df <= degreeR1)
             {
-                int[] q;
-                int[] coeff = new int[1];
-                coeff[0] = degreeR1 == -1 ? 0 : result[1][degreeR1];
-                q = MultWithElement(f, coeff[0]);
                 int n = degreeR1 - df;
-                q = MultWithMonomial(q, n);
-                coeff = MultWithMonomial(coeff, n);
-                result[0] = Add(coeff, result[0]);
-                result[1] = Add(q, result[1]);
-                degreeR1 = ComputeDegree(result[1]);
+                result[0][n] ^= 1;
+                AddAt(f, result[1], n);
+                degreeR1 = ComputeDegree(result[1], degreeR1 - 1);
             }
-            return result;
-        }
-
-        /**
-         * Compute the product of two polynomials over the field <tt>GF(2^m)</tt>
-         * using a Karatzuba like multiplication.
-         *
-         * @param a the first polynomial
-         * @param b the second polynomial
-         * @return a * b
-         */
-        private int[] Multiply(int[] a, int[] b)
-        {
-            int[] mult1, mult2;
-            if (ComputeDegree(a) < ComputeDegree(b))
-            {
-                mult1 = b;
-                mult2 = a;
-            }
-            else
-            {
-                mult1 = a;
-                mult2 = b;
-            }
-
-            mult1 = NormalForm(mult1);
-            mult2 = NormalForm(mult2);
-
-            if (mult2.Length == 1)
-                return MultWithElement(mult1, mult2[0]);
-
-            int d1 = mult1.Length;
-            int d2 = mult2.Length;
-            int[] result;
-
-            if (d2 != d1)
-            {
-                int[] res1 = new int[d2];
-                int[] res2 = new int[d1 - d2];
-                Array.Copy(mult1, 0, res1, 0, res1.Length);
-                Array.Copy(mult1, d2, res2, 0, res2.Length);
-                res1 = Multiply(res1, mult2);
-                res2 = Multiply(res2, mult2);
-                res2 = MultWithMonomial(res2, d2);
-                result = Add(res1, res2);
-            }
-            else
-            {
-                d2 = (int)((uint)(d1 + 1) >> 1);
-                int d = d1 - d2;
-                int[] firstPartMult1 = new int[d2];
-                int[] firstPartMult2 = new int[d2];
-                int[] secondPartMult1 = new int[d];
-                int[] secondPartMult2 = new int[d];
-                Array.Copy(mult1, 0, firstPartMult1, 0, firstPartMult1.Length);
-                Array.Copy(mult1, d2, secondPartMult1, 0, secondPartMult1.Length);
-                Array.Copy(mult2, 0, firstPartMult2, 0, firstPartMult2.Length);
-                Array.Copy(mult2, d2, secondPartMult2, 0, secondPartMult2.Length);
-                int[] helpPoly1 = Add(firstPartMult1, secondPartMult1);
-                int[] helpPoly2 = Add(firstPartMult2, secondPartMult2);
-                int[] res1 = Multiply(firstPartMult1, firstPartMult2);
-                int[] res2 = Multiply(helpPoly1, helpPoly2);
-                int[] res3 = Multiply(secondPartMult1, secondPartMult2);
-                res2 = Add(res2, res1);
-                res2 = Add(res2, res3);
-                res3 = MultWithMonomial(res3, d2);
-                result = Add(res2, res3);
-                result = MultWithMonomial(result, d2);
-                result = Add(result, res1);
-            }
-
+            result[1] = NormalForm(result[1]);
             return result;
         }
 
@@ -266,7 +167,7 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
          * @param f the reduction polynomial
          * @return <tt>a mod f</tt>
          */
-        private int[] Mod(int[] a, int[] f)
+        private static int[] Mod(int[] a, int[] f)
         {
             int df = ComputeDegree(f);
             if (df == -1)
@@ -277,13 +178,11 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
 
             while (df <= degreeR)
             {
-                int coeff = degreeR == -1 ? 0 : result[degreeR];
-                int[] q = MultWithMonomial(f, degreeR - df);
-                q = MultWithElement(q, coeff);
-                result = Add(q, result);
-                degreeR = ComputeDegree(result);
+                int n = degreeR - df;
+                AddAt(f, result, n);
+                degreeR = ComputeDegree(result, degreeR - 1);
             }
-            return result;
+            return NormalForm(result);
         }
 
         /**
@@ -295,8 +194,13 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
          */
         private static int ComputeDegree(int[] a)
         {
+            return ComputeDegree(a, a.Length - 1);
+        }
+
+        private static int ComputeDegree(int[] a, int from)
+        {
             int degree;
-            for (degree = a.Length - 1; degree >= 0 && a[degree] == 0; degree--)
+            for (degree = from; degree >= 0 && a[degree] == 0; degree--)
             {
             }
             return degree;
@@ -358,7 +262,7 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
             return new BikePolynomial(resultCoeff);
         }
 
-        private int[] ModInvBigDeg(int[] b, int[] g)
+        private static int[] ModInvBigDeg(int[] b, int[] g)
         {
             int[] r0 = NormalForm(g);
             int[] r1 = Mod(b, g);
@@ -387,7 +291,7 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
          * @param g the reduction polynomial
          * @return <tt>a * b mod g</tt>
          */
-        private int[] ModKaratsubaMultiplyBigDeg(int[] aa, int[] bb, int[] g)
+        private static int[] ModKaratsubaMultiplyBigDeg(int[] aa, int[] bb, int[] g)
         {
             int[] a, b;
             if (aa.Length >= bb.Length)
@@ -420,25 +324,17 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
                 for (int p = 0; p < pLimit; p++)
                 {
                     int q = i - p;
-
-                    int ap = a[p];
                     int aq = q < a.Length ? a[q] : 0;
 
-                    int bp = b[p];
-                    int dp = D[p];
-
                     if (q < m)
                     {
-                        int bq = b[q];
-                        int dq = D[q];
-
-                        S[i] = S[i] + (ap + aq) * (bp + bq);
-                        T[i] = T[i] + dp + dq;
+                        S[i] += (a[p] + aq) * (b[p] + b[q]);
+                        T[i] += D[p] + D[q];
                     }
                     else if (q < n)
                     {
-                        S[i] = S[i] + ((ap + aq) * bp);
-                        T[i] = T[i] + dp;
+                        S[i] += (a[p] + aq) * b[p];
+                        T[i] += D[p];
                     }
                 }
             }
diff --git a/crypto/src/pqc/crypto/bike/BikePrivateKeyParameters.cs b/crypto/src/pqc/crypto/bike/BikePrivateKeyParameters.cs
index d8c6e4613..dce003a7b 100644
--- a/crypto/src/pqc/crypto/bike/BikePrivateKeyParameters.cs
+++ b/crypto/src/pqc/crypto/bike/BikePrivateKeyParameters.cs
@@ -1,11 +1,9 @@
 using Org.BouncyCastle.Utilities;
-using System;
-using System.Collections.Generic;
-using System.Text;
 
 namespace Org.BouncyCastle.Pqc.Crypto.Bike
 {
-    public class BikePrivateKeyParameters : BikeKeyParameters
+    public class BikePrivateKeyParameters
+        : BikeKeyParameters
     {
         // h0
         private byte[] h0;
@@ -23,7 +21,8 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
          * @param h1    h1
          * @param sigma random bytes sigma
          */
-        public BikePrivateKeyParameters(BikeParameters bikeParameters, byte[] h0, byte[] h1, byte[] sigma) : base(true, bikeParameters)
+        public BikePrivateKeyParameters(BikeParameters bikeParameters, byte[] h0, byte[] h1, byte[] sigma)
+            : base(true, bikeParameters)
         {
             this.h0 = Arrays.Clone(h0);
             this.h1 = Arrays.Clone(h1);
@@ -45,7 +44,7 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
             return sigma;
         }
 
-        public byte[] PrivateKey => Arrays.Concatenate(Arrays.Concatenate(h0, h1), sigma);
+        internal byte[] PrivateKey => Arrays.Concatenate(Arrays.Concatenate(h0, h1), sigma);
 
         public byte[] GetEncoded()
         {
diff --git a/crypto/src/pqc/crypto/bike/BikePublicKeyParameters.cs b/crypto/src/pqc/crypto/bike/BikePublicKeyParameters.cs
index 16370c3cf..dbbe2480c 100644
--- a/crypto/src/pqc/crypto/bike/BikePublicKeyParameters.cs
+++ b/crypto/src/pqc/crypto/bike/BikePublicKeyParameters.cs
@@ -1,28 +1,28 @@
 using Org.BouncyCastle.Utilities;
-using System;
-using System.Collections.Generic;
-using System.Text;
 
 namespace Org.BouncyCastle.Pqc.Crypto.Bike
 {
-    public class BikePublicKeyParameters : BikeKeyParameters
+    public class BikePublicKeyParameters
+        : BikeKeyParameters
     {
-        byte[] publicKey;
+        private readonly byte[] publicKey;
 
         /**
          * Constructor.
          *
          * @param publicKey      byte
          */
-        public BikePublicKeyParameters(BikeParameters param, byte[] publicKey) : base(false, param)
+        public BikePublicKeyParameters(BikeParameters param, byte[] publicKey)
+            : base(false, param)
         {
             this.publicKey = Arrays.Clone(publicKey);
         }
 
-       public byte[] PublicKey => Arrays.Clone(publicKey);
+        internal byte[] PublicKey => publicKey;
+
         public byte[] GetEncoded()
         {
-            return PublicKey;
+            return Arrays.Clone(publicKey);
         }
     }
 }
diff --git a/crypto/src/pqc/crypto/bike/BikeRandomGenerator.cs b/crypto/src/pqc/crypto/bike/BikeRandomGenerator.cs
deleted file mode 100644
index 7117c1d9d..000000000
--- a/crypto/src/pqc/crypto/bike/BikeRandomGenerator.cs
+++ /dev/null
@@ -1,64 +0,0 @@
-using Org.BouncyCastle.Crypto;
-using Org.BouncyCastle.Crypto.Utilities;
-using Org.BouncyCastle.Utilities;
-
-namespace Org.BouncyCastle.Pqc.Crypto.Bike
-{
-    internal class BikeRandomGenerator
-    {
-        private static int GetRandomInMod(int mod, IXof digest)
-        {
-            int highest = Integers.HighestOneBit(mod);
-            int mask = highest | (highest - 1);
-            while (true)
-            {
-                int res = GetRandomNumber(digest) & mask;
-                if (res < mod)
-                    return res;
-            }
-        }
-
-        private static void GenerateRandomArray(byte[] res, int mod, int weight, IXof digest)
-        {
-            int index = 0;
-            while (index < weight)
-            {
-                int tmp = GetRandomInMod(mod, digest);
-
-                if (CheckBit(res, tmp) == 0)
-                { // check for new index
-                    SetBit(res, tmp);
-                    index++;
-                }
-            }
-        }
-
-        private static int CheckBit(byte[] a, int position)
-        {
-            int index = position / 8;
-            int pos = position % 8;
-            return ((a[index] >> (pos)) & 0x01);
-        }
-
-        private static void SetBit(byte[] a, int position)
-        {
-            int index = position / 8;
-            int pos = position % 8;
-            a[index] |= (byte) (1 << (pos));
-        }
-
-        public static byte[] GenerateRandomByteArray(int mod, int size, int weight, IXof digest)
-        {
-            byte[] res = new byte[size];
-            GenerateRandomArray(res, mod, weight, digest);
-            return res;
-        }
-
-        private static int GetRandomNumber(IXof digest)
-        {
-            byte[] output = new byte[4];
-            digest.Output(output, 0, output.Length);
-            return (int)Pack.LE_To_UInt32(output, 0);
-        }
-    }
-}
diff --git a/crypto/src/pqc/crypto/bike/Utils.cs b/crypto/src/pqc/crypto/bike/BikeUtilities.cs
index 5d151f522..5facdaacf 100644
--- a/crypto/src/pqc/crypto/bike/Utils.cs
+++ b/crypto/src/pqc/crypto/bike/BikeUtilities.cs
@@ -1,8 +1,12 @@
 using System;
 
+using Org.BouncyCastle.Crypto.Utilities;
+using Org.BouncyCastle.Crypto;
+using Org.BouncyCastle.Utilities;
+
 namespace Org.BouncyCastle.Pqc.Crypto.Bike
 {
-    internal class Utils
+    internal class BikeUtilities
     {
         internal static byte[] XorBytes(byte[] a, byte[] b, int size)
         {
@@ -100,5 +104,36 @@ namespace Org.BouncyCastle.Pqc.Crypto.Bike
             Array.Copy(input, 0, output, 0, input.Length);
             return output;
         }
+
+        internal static byte[] GenerateRandomByteArray(int mod, int size, int weight, IXof digest)
+        {
+            byte[] buf = new byte[4];
+            int highest = Integers.HighestOneBit(mod);
+            int mask = highest | (highest - 1);
+
+            byte[] res = new byte[size];
+            int count = 0;
+            while (count < weight)
+            {
+                digest.Output(buf, 0, 4);
+                int tmp = (int)Pack.LE_To_UInt32(buf) & mask;
+
+                if (tmp < mod && SetBit(res, tmp))
+                {
+                    ++count;
+                }
+            }
+            return res;
+        }
+
+        private static bool SetBit(byte[] a, int position)
+        {
+            int index = position / 8;
+            int pos = position % 8;
+            int selector = 1 << pos;
+            bool result = (a[index] & selector) == 0;
+            a[index] |= (byte)selector;
+            return result;
+        }
     }
 }
diff --git a/crypto/test/src/pqc/crypto/test/BikeVectorTest.cs b/crypto/test/src/pqc/crypto/test/BikeVectorTest.cs
index 723f6b554..a25a27fe1 100644
--- a/crypto/test/src/pqc/crypto/test/BikeVectorTest.cs
+++ b/crypto/test/src/pqc/crypto/test/BikeVectorTest.cs
@@ -64,11 +64,13 @@ namespace Org.BouncyCastle.Pqc.Crypto.Tests
             kpGen.Init(genParam);
             AsymmetricCipherKeyPair kp = kpGen.GenerateKeyPair();
 
-            BikePublicKeyParameters pubParams = (BikePublicKeyParameters)PublicKeyFactory.CreateKey(SubjectPublicKeyInfoFactory.CreateSubjectPublicKeyInfo((BikePublicKeyParameters) kp.Public));
-            BikePrivateKeyParameters privParams = (BikePrivateKeyParameters)PrivateKeyFactory.CreateKey(PrivateKeyInfoFactory.CreatePrivateKeyInfo((BikePrivateKeyParameters) kp.Private));
+            BikePublicKeyParameters pubParams = (BikePublicKeyParameters)PublicKeyFactory.CreateKey(
+                SubjectPublicKeyInfoFactory.CreateSubjectPublicKeyInfo((BikePublicKeyParameters) kp.Public));
+            BikePrivateKeyParameters privParams = (BikePrivateKeyParameters)PrivateKeyFactory.CreateKey(
+                PrivateKeyInfoFactory.CreatePrivateKeyInfo((BikePrivateKeyParameters) kp.Private));
 
-            Assert.True(Arrays.AreEqual(pk, pubParams.PublicKey), name + " " + count + ": public key");
-            Assert.True(Arrays.AreEqual(sk, privParams.PrivateKey), name + " " + count + ": secret key");
+            Assert.True(Arrays.AreEqual(pk, pubParams.GetEncoded()), name + " " + count + ": public key");
+            Assert.True(Arrays.AreEqual(sk, privParams.GetEncoded()), name + " " + count + ": secret key");
 
             // KEM Enc
             BikeKemGenerator BikeEncCipher = new BikeKemGenerator(random);