Using `using` local variable declarations in C# examples (yay for C# 8.0)

This commit is contained in:
Kim Laine 2020-02-01 19:30:30 -08:00
Родитель f26e5041f1
Коммит 0389ed6a51
8 изменённых файлов: 338 добавлений и 256 удалений

Просмотреть файл

@ -42,7 +42,7 @@ namespace SEALNetExamples
be large enough to support the desired computation; otherwise the result is
impossible to make sense of even with the secret key.
*/
EncryptionParameters parms = new EncryptionParameters(SchemeType.BFV);
using EncryptionParameters parms = new EncryptionParameters(SchemeType.BFV);
/*
The first parameter we set is the degree of the `polynomial modulus'. This
@ -124,8 +124,21 @@ namespace SEALNetExamples
Now that all parameters are set, we are ready to construct a SEALContext
object. This is a heavy class that checks the validity and properties of the
parameters we just set.
C# 8.0 introduced the `using` declaration for local variables. This is a very
convenient addition to the language: it causes the Dispose method for the
object to be called at the end of the enclosing scope (in this case the end
of this function), hence automatically releasing the native resources held by
the object. This is helpful, because releasing the native resources returns
the allocated memory to the memory pool, speeding up further allocations.
Another way would be to call GC::Collect() at a convenient point in the code,
but this may be less optimal as it may still cause unnecessary allocations
of memory if native resources were not released early enough. In this program
we call GC::Collect() after every example (see Examples.cs) to make sure
everything is returned to the memory pool at latest before running the next
example.
*/
SEALContext context = new SEALContext(parms);
using SEALContext context = new SEALContext(parms);
/*
Print the parameters that we have chosen.
@ -150,29 +163,29 @@ namespace SEALNetExamples
automatically generates the public and secret key, which can immediately be
read to local variables.
*/
KeyGenerator keygen = new KeyGenerator(context);
PublicKey publicKey = keygen.PublicKey;
SecretKey secretKey = keygen.SecretKey;
using KeyGenerator keygen = new KeyGenerator(context);
using PublicKey publicKey = keygen.PublicKey;
using SecretKey secretKey = keygen.SecretKey;
/*
To be able to encrypt we need to construct an instance of Encryptor. Note
that the Encryptor only requires the public key, as expected.
*/
Encryptor encryptor = new Encryptor(context, publicKey);
using Encryptor encryptor = new Encryptor(context, publicKey);
/*
Computations on the ciphertexts are performed with the Evaluator class. In
a real use-case the Evaluator would not be constructed by the same party
that holds the secret key.
*/
Evaluator evaluator = new Evaluator(context);
using Evaluator evaluator = new Evaluator(context);
/*
We will of course want to decrypt our results to verify that everything worked,
so we need to also construct an instance of Decryptor. Note that the Decryptor
requires the secret key.
*/
Decryptor decryptor = new Decryptor(context, secretKey);
using Decryptor decryptor = new Decryptor(context, secretKey);
/*
As an example, we evaluate the degree 4 polynomial
@ -199,14 +212,14 @@ namespace SEALNetExamples
*/
Utilities.PrintLine();
int x = 6;
Plaintext xPlain = new Plaintext(x.ToString());
using Plaintext xPlain = new Plaintext(x.ToString());
Console.WriteLine($"Express x = {x} as a plaintext polynomial 0x{xPlain}.");
/*
We then encrypt the plaintext, producing a ciphertext.
*/
Utilities.PrintLine();
Ciphertext xEncrypted = new Ciphertext();
using Ciphertext xEncrypted = new Ciphertext();
Console.WriteLine("Encrypt xPlain to xEncrypted.");
encryptor.Encrypt(xPlain, xEncrypted);
@ -229,7 +242,7 @@ namespace SEALNetExamples
We decrypt the ciphertext and print the resulting plaintext in order to
demonstrate correctness of the encryption.
*/
Plaintext xDecrypted = new Plaintext();
using Plaintext xDecrypted = new Plaintext();
Console.Write(" + decryption of encrypted_x: ");
decryptor.Decrypt(xEncrypted, xDecrypted);
Console.WriteLine($"0x{xDecrypted} ...... Correct.");
@ -254,9 +267,9 @@ namespace SEALNetExamples
*/
Utilities.PrintLine();
Console.WriteLine("Compute xSqPlusOne (x^2+1).");
Ciphertext xSqPlusOne = new Ciphertext();
using Ciphertext xSqPlusOne = new Ciphertext();
evaluator.Square(xEncrypted, xSqPlusOne);
Plaintext plainOne = new Plaintext("1");
using Plaintext plainOne = new Plaintext("1");
evaluator.AddPlainInplace(xSqPlusOne, plainOne);
/*
@ -274,7 +287,7 @@ namespace SEALNetExamples
Even though the size has grown, decryption works as usual as long as noise
budget has not reached 0.
*/
Plaintext decryptedResult = new Plaintext();
using Plaintext decryptedResult = new Plaintext();
Console.Write(" + decryption of xSqPlusOne: ");
decryptor.Decrypt(xSqPlusOne, decryptedResult);
Console.WriteLine($"0x{decryptedResult} ...... Correct.");
@ -284,7 +297,7 @@ namespace SEALNetExamples
*/
Utilities.PrintLine();
Console.WriteLine("Compute xPlusOneSq ((x+1)^2).");
Ciphertext xPlusOneSq = new Ciphertext();
using Ciphertext xPlusOneSq = new Ciphertext();
evaluator.AddPlain(xEncrypted, plainOne, xPlusOneSq);
evaluator.SquareInplace(xPlusOneSq);
Console.WriteLine($" + size of xPlusOneSq: {xPlusOneSq.Size}");
@ -299,8 +312,8 @@ namespace SEALNetExamples
*/
Utilities.PrintLine();
Console.WriteLine("Compute encryptedResult (4(x^2+1)(x+1)^2).");
Ciphertext encryptedResult = new Ciphertext();
Plaintext plainFour = new Plaintext("4");
using Ciphertext encryptedResult = new Ciphertext();
using Plaintext plainFour = new Plaintext("4");
evaluator.MultiplyPlainInplace(xSqPlusOne, plainFour);
evaluator.Multiply(xSqPlusOne, xPlusOneSq, encryptedResult);
Console.WriteLine($" + size of encrypted_result: {encryptedResult.Size}");
@ -341,7 +354,7 @@ namespace SEALNetExamples
*/
Utilities.PrintLine();
Console.WriteLine("Generate locally usable relinearization keys.");
RelinKeys relinKeys = keygen.RelinKeysLocal();
using RelinKeys relinKeys = keygen.RelinKeysLocal();
/*
We now repeat the computation relinearizing after each multiplication.
@ -349,7 +362,7 @@ namespace SEALNetExamples
Utilities.PrintLine();
Console.WriteLine("Compute and relinearize xSquared (x^2),");
Console.WriteLine(new string(' ', 13) + "then compute xSqPlusOne (x^2+1)");
Ciphertext xSquared = new Ciphertext();
using Ciphertext xSquared = new Ciphertext();
evaluator.Square(xEncrypted, xSquared);
Console.WriteLine($" + size of xSquared: {xSquared.Size}");
evaluator.RelinearizeInplace(xSquared, relinKeys);
@ -363,7 +376,7 @@ namespace SEALNetExamples
Console.WriteLine($"0x{decryptedResult} ...... Correct.");
Utilities.PrintLine();
Ciphertext xPlusOne = new Ciphertext();
using Ciphertext xPlusOne = new Ciphertext();
Console.WriteLine("Compute xPlusOne (x+1),");
Console.WriteLine(new string(' ', 13) +
"then compute and relinearize xPlusOneSq ((x+1)^2).");

Просмотреть файл

@ -72,7 +72,7 @@ namespace SEALNetExamples
However, advanced users will probably prefer more efficient approaches,
such as the BatchEncoder or the CKKSEncoder.
*/
EncryptionParameters parms = new EncryptionParameters(SchemeType.BFV);
using EncryptionParameters parms = new EncryptionParameters(SchemeType.BFV);
ulong polyModulusDegree = 4096;
parms.PolyModulusDegree = polyModulusDegree;
parms.CoeffModulus = CoeffModulus.BFVDefault(polyModulusDegree);
@ -84,41 +84,41 @@ namespace SEALNetExamples
will be incorrect.
*/
parms.PlainModulus = new SmallModulus(512);
SEALContext context = new SEALContext(parms);
using SEALContext context = new SEALContext(parms);
Utilities.PrintParameters(context);
Console.WriteLine();
KeyGenerator keygen = new KeyGenerator(context);
PublicKey publicKey = keygen.PublicKey;
SecretKey secretKey = keygen.SecretKey;
Encryptor encryptor = new Encryptor(context, publicKey);
Evaluator evaluator = new Evaluator(context);
Decryptor decryptor = new Decryptor(context, secretKey);
using KeyGenerator keygen = new KeyGenerator(context);
using PublicKey publicKey = keygen.PublicKey;
using SecretKey secretKey = keygen.SecretKey;
using Encryptor encryptor = new Encryptor(context, publicKey);
using Evaluator evaluator = new Evaluator(context);
using Decryptor decryptor = new Decryptor(context, secretKey);
/*
We create an IntegerEncoder.
*/
IntegerEncoder encoder = new IntegerEncoder(context);
using IntegerEncoder encoder = new IntegerEncoder(context);
/*
First, we encode two integers as plaintext polynomials. Note that encoding
is not encryption: at this point nothing is encrypted.
*/
int value1 = 5;
Plaintext plain1 = encoder.Encode(value1);
using Plaintext plain1 = encoder.Encode(value1);
Utilities.PrintLine();
Console.WriteLine($"Encode {value1} as polynomial {plain1} (plain1),");
int value2 = -7;
Plaintext plain2 = encoder.Encode(value2);
using Plaintext plain2 = encoder.Encode(value2);
Console.WriteLine(new string(' ', 13)
+ $"Encode {value2} as polynomial {plain2} (plain2),");
/*
Now we can encrypt the plaintext polynomials.
*/
Ciphertext encrypted1 = new Ciphertext();
Ciphertext encrypted2 = new Ciphertext();
using Ciphertext encrypted1 = new Ciphertext();
using Ciphertext encrypted2 = new Ciphertext();
Utilities.PrintLine();
Console.WriteLine("Encrypt plain1 to encrypted1 and plain2 to encrypted2.");
encryptor.Encrypt(plain1, encrypted1);
@ -132,7 +132,7 @@ namespace SEALNetExamples
As a simple example, we compute (-encrypted1 + encrypted2) * encrypted2.
*/
encryptor.Encrypt(plain2, encrypted2);
Ciphertext encryptedResult = new Ciphertext();
using Ciphertext encryptedResult = new Ciphertext();
Utilities.PrintLine();
Console.WriteLine("Compute encrypted_result = (-encrypted1 + encrypted2) * encrypted2.");
evaluator.Negate(encrypted1, encryptedResult);
@ -141,7 +141,7 @@ namespace SEALNetExamples
Console.WriteLine(" + Noise budget in encryptedResult: {0} bits",
decryptor.InvariantNoiseBudget(encryptedResult));
Plaintext plainResult = new Plaintext();
using Plaintext plainResult = new Plaintext();
Utilities.PrintLine();
Console.WriteLine("Decrypt encrypted_result to plain_result.");
decryptor.Decrypt(encryptedResult, plainResult);
@ -177,7 +177,7 @@ namespace SEALNetExamples
with BFV, and when used properly will result in implementations outperforming
anything done with the IntegerEncoder.
*/
EncryptionParameters parms = new EncryptionParameters(SchemeType.BFV);
using EncryptionParameters parms = new EncryptionParameters(SchemeType.BFV);
ulong polyModulusDegree = 8192;
parms.PolyModulusDegree = polyModulusDegree;
parms.CoeffModulus = CoeffModulus.BFVDefault(polyModulusDegree);
@ -190,7 +190,7 @@ namespace SEALNetExamples
*/
parms.PlainModulus = PlainModulus.Batching(polyModulusDegree, 20);
SEALContext context = new SEALContext(parms);
using SEALContext context = new SEALContext(parms);
Utilities.PrintParameters(context);
Console.WriteLine();
@ -198,21 +198,21 @@ namespace SEALNetExamples
We can verify that batching is indeed enabled by looking at the encryption
parameter qualifiers created by SEALContext.
*/
var qualifiers = context.FirstContextData.Qualifiers;
using var qualifiers = context.FirstContextData.Qualifiers;
Console.WriteLine($"Batching enabled: {qualifiers.UsingBatching}");
KeyGenerator keygen = new KeyGenerator(context);
PublicKey publicKey = keygen.PublicKey;
SecretKey secretKey = keygen.SecretKey;
RelinKeys relinKeys = keygen.RelinKeysLocal();
Encryptor encryptor = new Encryptor(context, publicKey);
Evaluator evaluator = new Evaluator(context);
Decryptor decryptor = new Decryptor(context, secretKey);
using KeyGenerator keygen = new KeyGenerator(context);
using PublicKey publicKey = keygen.PublicKey;
using SecretKey secretKey = keygen.SecretKey;
using RelinKeys relinKeys = keygen.RelinKeysLocal();
using Encryptor encryptor = new Encryptor(context, publicKey);
using Evaluator evaluator = new Evaluator(context);
using Decryptor decryptor = new Decryptor(context, secretKey);
/*
Batching is done through an instance of the BatchEncoder class.
*/
BatchEncoder batchEncoder = new BatchEncoder(context);
using BatchEncoder batchEncoder = new BatchEncoder(context);
/*
The total number of batching `slots' equals the PolyModulusDegree, N, and
@ -247,7 +247,7 @@ namespace SEALNetExamples
/*
First we use BatchEncoder to encode the matrix into a plaintext polynomial.
*/
Plaintext plainMatrix = new Plaintext();
using Plaintext plainMatrix = new Plaintext();
Utilities.PrintLine();
Console.WriteLine("Encode plaintext matrix:");
batchEncoder.Encode(podMatrix, plainMatrix);
@ -264,7 +264,7 @@ namespace SEALNetExamples
/*
Next we encrypt the encoded plaintext.
*/
Ciphertext encryptedMatrix = new Ciphertext();
using Ciphertext encryptedMatrix = new Ciphertext();
Utilities.PrintLine();
Console.WriteLine("Encrypt plainMatrix to encryptedMatrix.");
encryptor.Encrypt(plainMatrix, encryptedMatrix);
@ -286,7 +286,7 @@ namespace SEALNetExamples
{
podMatrix2[i] = (i % 2) + 1;
}
Plaintext plainMatrix2 = new Plaintext();
using Plaintext plainMatrix2 = new Plaintext();
batchEncoder.Encode(podMatrix2, plainMatrix2);
Console.WriteLine();
Console.WriteLine("Second input plaintext matrix:");
@ -311,7 +311,7 @@ namespace SEALNetExamples
/*
We decrypt and decompose the plaintext to recover the result as a matrix.
*/
Plaintext plainResult = new Plaintext();
using Plaintext plainResult = new Plaintext();
Utilities.PrintLine();
Console.WriteLine("Decrypt and decode result.");
decryptor.Decrypt(encryptedMatrix, plainResult);
@ -349,7 +349,7 @@ namespace SEALNetExamples
`CKKS_Basics.cs'. In this example we use CoeffModulus.Create to
generate 5 40-bit prime numbers.
*/
EncryptionParameters parms = new EncryptionParameters(SchemeType.CKKS);
using EncryptionParameters parms = new EncryptionParameters(SchemeType.CKKS);
ulong polyModulusDegree = 8192;
parms.PolyModulusDegree = polyModulusDegree;
@ -359,24 +359,24 @@ namespace SEALNetExamples
/*
We create the SEALContext as usual and print the parameters.
*/
SEALContext context = new SEALContext(parms);
using SEALContext context = new SEALContext(parms);
Utilities.PrintParameters(context);
Console.WriteLine();
/*
Keys are created the same way as for the BFV scheme.
*/
KeyGenerator keygen = new KeyGenerator(context);
PublicKey publicKey = keygen.PublicKey;
SecretKey secretKey = keygen.SecretKey;
RelinKeys relinKeys = keygen.RelinKeysLocal();
using KeyGenerator keygen = new KeyGenerator(context);
using PublicKey publicKey = keygen.PublicKey;
using SecretKey secretKey = keygen.SecretKey;
using RelinKeys relinKeys = keygen.RelinKeysLocal();
/*
We also set up an Encryptor, Evaluator, and Decryptor as usual.
*/
Encryptor encryptor = new Encryptor(context, publicKey);
Evaluator evaluator = new Evaluator(context);
Decryptor decryptor = new Decryptor(context, secretKey);
using Encryptor encryptor = new Encryptor(context, publicKey);
using Evaluator evaluator = new Evaluator(context);
using Decryptor decryptor = new Decryptor(context, secretKey);
/*
To create CKKS plaintexts we need a special encoder: there is no other way
@ -386,7 +386,7 @@ namespace SEALNetExamples
looks a lot like what BatchEncoder does for the BFV scheme, but the theory
behind it is completely different.
*/
CKKSEncoder encoder = new CKKSEncoder(context);
using CKKSEncoder encoder = new CKKSEncoder(context);
/*
In CKKS the number of slots is PolyModulusDegree / 2 and each slot encodes
@ -419,7 +419,7 @@ namespace SEALNetExamples
we have little to worry about in this regard. For this simple example a 30-bit
scale is more than enough.
*/
Plaintext plain = new Plaintext();
using Plaintext plain = new Plaintext();
double scale = Math.Pow(2.0, 30);
Utilities.PrintLine();
Console.WriteLine("Encode input vector.");
@ -436,7 +436,7 @@ namespace SEALNetExamples
/*
The vector is encrypted the same was as in BFV.
*/
Ciphertext encrypted = new Ciphertext();
using Ciphertext encrypted = new Ciphertext();
Utilities.PrintLine();
Console.WriteLine("Encrypt input vector, square, and relinearize.");
encryptor.Encrypt(plain, encrypted);

Просмотреть файл

@ -44,7 +44,7 @@ namespace SEALNetExamples
node can be identified by the ParmsId of its specific encryption parameters
(PolyModulusDegree remains the same but CoeffModulus varies).
*/
EncryptionParameters parms = new EncryptionParameters(SchemeType.BFV);
using EncryptionParameters parms = new EncryptionParameters(SchemeType.BFV);
ulong polyModulusDegree = 8192;
parms.PolyModulusDegree = polyModulusDegree;
@ -91,7 +91,7 @@ namespace SEALNetExamples
*/
parms.PlainModulus = PlainModulus.Batching(polyModulusDegree, 20);
SEALContext context = new SEALContext(parms);
using SEALContext context = new SEALContext(parms);
Utilities.PrintParameters(context);
/*
@ -164,10 +164,10 @@ namespace SEALNetExamples
/*
We create some keys and check that indeed they appear at the highest level.
*/
KeyGenerator keygen = new KeyGenerator(context);
PublicKey publicKey = keygen.PublicKey;
SecretKey secretKey = keygen.SecretKey;
RelinKeys relinKeys = keygen.RelinKeysLocal();
using KeyGenerator keygen = new KeyGenerator(context);
using PublicKey publicKey = keygen.PublicKey;
using SecretKey secretKey = keygen.SecretKey;
using RelinKeys relinKeys = keygen.RelinKeysLocal();
/*
In this example we create a local version of the GaloisKeys object using
@ -176,7 +176,7 @@ namespace SEALNetExamples
use KeyGenerator.GaloisKeys(), which outputs a Serializable<GaloisKeys>
object for compressed serialization.
*/
GaloisKeys galoisKeys = keygen.GaloisKeysLocal();
using GaloisKeys galoisKeys = keygen.GaloisKeysLocal();
Utilities.PrintLine();
Console.WriteLine("Print the parameter IDs of generated elements.");
Console.WriteLine($" + publicKey: {publicKey.ParmsId}");
@ -184,16 +184,16 @@ namespace SEALNetExamples
Console.WriteLine($" + relinKeys: {relinKeys.ParmsId}");
Console.WriteLine($" + galoisKeys: {galoisKeys.ParmsId}");
Encryptor encryptor = new Encryptor(context, publicKey);
Evaluator evaluator = new Evaluator(context);
Decryptor decryptor = new Decryptor(context, secretKey);
using Encryptor encryptor = new Encryptor(context, publicKey);
using Evaluator evaluator = new Evaluator(context);
using Decryptor decryptor = new Decryptor(context, secretKey);
/*
In the BFV scheme plaintexts do not carry a ParmsId, but ciphertexts do. Note
how the freshly encrypted ciphertext is at the highest data level.
*/
Plaintext plain = new Plaintext("1x^3 + 2x^2 + 3x^1 + 4");
Ciphertext encrypted = new Ciphertext();
using Plaintext plain = new Plaintext("1x^3 + 2x^2 + 3x^1 + 4");
using Ciphertext encrypted = new Ciphertext();
encryptor.Encrypt(plain, encrypted);
Console.WriteLine($" + plain: {plain.ParmsId} (not set in BFV)");
Console.WriteLine($" + encrypted: {encrypted.ParmsId}");
@ -309,7 +309,7 @@ namespace SEALNetExamples
not want to create the modulus switching chain, except for the highest two
levels. This can be done by passing a bool `false' to SEALContext constructor.
*/
context = new SEALContext(parms, expandModChain: false);
using SEALContext context2 = new SEALContext(parms, expandModChain: false);
/*
We can check that indeed the modulus switching chain has been created only
@ -320,7 +320,7 @@ namespace SEALNetExamples
Utilities.PrintLine();
Console.WriteLine("Print the modulus switching chain.");
Console.Write("----> ");
for (contextData = context.KeyContextData; null != contextData;
for (contextData = context2.KeyContextData; null != contextData;
contextData = contextData.NextContextData)
{
Console.WriteLine($"Level (chain index): {contextData.ChainIndex}");

Просмотреть файл

@ -24,7 +24,7 @@ namespace SEALNetExamples
We start by setting up the CKKS scheme.
*/
EncryptionParameters parms = new EncryptionParameters(SchemeType.CKKS);
using EncryptionParameters parms = new EncryptionParameters(SchemeType.CKKS);
/*
We saw in `2_Encoders.cs' that multiplication in CKKS causes scales in
@ -86,19 +86,19 @@ namespace SEALNetExamples
*/
double scale = Math.Pow(2.0, 40);
SEALContext context = new SEALContext(parms);
using SEALContext context = new SEALContext(parms);
Utilities.PrintParameters(context);
Console.WriteLine();
KeyGenerator keygen = new KeyGenerator(context);
PublicKey publicKey = keygen.PublicKey;
SecretKey secretKey = keygen.SecretKey;
RelinKeys relinKeys = keygen.RelinKeysLocal();
Encryptor encryptor = new Encryptor(context, publicKey);
Evaluator evaluator = new Evaluator(context);
Decryptor decryptor = new Decryptor(context, secretKey);
using KeyGenerator keygen = new KeyGenerator(context);
using PublicKey publicKey = keygen.PublicKey;
using SecretKey secretKey = keygen.SecretKey;
using RelinKeys relinKeys = keygen.RelinKeysLocal();
using Encryptor encryptor = new Encryptor(context, publicKey);
using Evaluator evaluator = new Evaluator(context);
using Decryptor decryptor = new Decryptor(context, secretKey);
CKKSEncoder encoder = new CKKSEncoder(context);
using CKKSEncoder encoder = new CKKSEncoder(context);
ulong slotCount = encoder.SlotCount;
Console.WriteLine($"Number of slots: {slotCount}");
@ -117,25 +117,25 @@ namespace SEALNetExamples
We create plaintexts for PI, 0.4, and 1 using an overload of CKKSEncoder.Encode
that encodes the given floating-point value to every slot in the vector.
*/
Plaintext plainCoeff3 = new Plaintext(),
plainCoeff1 = new Plaintext(),
plainCoeff0 = new Plaintext();
using Plaintext plainCoeff3 = new Plaintext(),
plainCoeff1 = new Plaintext(),
plainCoeff0 = new Plaintext();
encoder.Encode(3.14159265, scale, plainCoeff3);
encoder.Encode(0.4, scale, plainCoeff1);
encoder.Encode(1.0, scale, plainCoeff0);
Plaintext xPlain = new Plaintext();
using Plaintext xPlain = new Plaintext();
Utilities.PrintLine();
Console.WriteLine("Encode input vectors.");
encoder.Encode(input, scale, xPlain);
Ciphertext x1Encrypted = new Ciphertext();
using Ciphertext x1Encrypted = new Ciphertext();
encryptor.Encrypt(xPlain, x1Encrypted);
/*
To compute x^3 we first compute x^2 and relinearize. However, the scale has
now grown to 2^80.
*/
Ciphertext x3Encrypted = new Ciphertext();
using Ciphertext x3Encrypted = new Ciphertext();
Utilities.PrintLine();
Console.WriteLine("Compute x^2 and relinearize:");
evaluator.Square(x1Encrypted, x3Encrypted);
@ -165,7 +165,7 @@ namespace SEALNetExamples
*/
Utilities.PrintLine();
Console.WriteLine("Compute and rescale PI*x.");
Ciphertext x1EncryptedCoeff3 = new Ciphertext();
using Ciphertext x1EncryptedCoeff3 = new Ciphertext();
evaluator.MultiplyPlain(x1Encrypted, plainCoeff3, x1EncryptedCoeff3);
Console.WriteLine(" + Scale of PI*x before rescale: {0} bits",
Math.Log(x1EncryptedCoeff3.Scale, newBase: 2));
@ -284,14 +284,14 @@ namespace SEALNetExamples
*/
Utilities.PrintLine();
Console.WriteLine("Compute PI*x^3 + 0.4*x + 1.");
Ciphertext encryptedResult = new Ciphertext();
using Ciphertext encryptedResult = new Ciphertext();
evaluator.Add(x3Encrypted, x1Encrypted, encryptedResult);
evaluator.AddPlainInplace(encryptedResult, plainCoeff0);
/*
First print the true result.
*/
Plaintext plainResult = new Plaintext();
using Plaintext plainResult = new Plaintext();
Utilities.PrintLine();
Console.WriteLine("Decrypt and decode PI * x ^ 3 + 0.4x + 1.");
Console.WriteLine(" + Expected result:");

Просмотреть файл

@ -18,26 +18,26 @@ namespace SEALNetExamples
{
Utilities.PrintExampleBanner("Example: Rotation / Rotation in BFV");
EncryptionParameters parms = new EncryptionParameters(SchemeType.BFV);
using EncryptionParameters parms = new EncryptionParameters(SchemeType.BFV);
ulong polyModulusDegree = 8192;
parms.PolyModulusDegree = polyModulusDegree;
parms.CoeffModulus = CoeffModulus.BFVDefault(polyModulusDegree);
parms.PlainModulus = PlainModulus.Batching(polyModulusDegree, 20);
SEALContext context = new SEALContext(parms);
using SEALContext context = new SEALContext(parms);
Utilities.PrintParameters(context);
Console.WriteLine();
KeyGenerator keygen = new KeyGenerator(context);
PublicKey publicKey = keygen.PublicKey;
SecretKey secretKey = keygen.SecretKey;
RelinKeys relinKeys = keygen.RelinKeysLocal();
Encryptor encryptor = new Encryptor(context, publicKey);
Evaluator evaluator = new Evaluator(context);
Decryptor decryptor = new Decryptor(context, secretKey);
using KeyGenerator keygen = new KeyGenerator(context);
using PublicKey publicKey = keygen.PublicKey;
using SecretKey secretKey = keygen.SecretKey;
using RelinKeys relinKeys = keygen.RelinKeysLocal();
using Encryptor encryptor = new Encryptor(context, publicKey);
using Evaluator evaluator = new Evaluator(context);
using Decryptor decryptor = new Decryptor(context, secretKey);
BatchEncoder batchEncoder = new BatchEncoder(context);
using BatchEncoder batchEncoder = new BatchEncoder(context);
ulong slotCount = batchEncoder.SlotCount;
ulong rowSize = slotCount / 2;
Console.WriteLine($"Plaintext matrix row size: {rowSize}");
@ -61,10 +61,10 @@ namespace SEALNetExamples
the plaintext as usual.
*/
Utilities.PrintLine();
Plaintext plainMatrix = new Plaintext();
using Plaintext plainMatrix = new Plaintext();
Console.WriteLine("Encode and encrypt.");
batchEncoder.Encode(podMatrix, plainMatrix);
Ciphertext encryptedMatrix = new Ciphertext();
using Ciphertext encryptedMatrix = new Ciphertext();
encryptor.Encrypt(plainMatrix, encryptedMatrix);
Console.WriteLine(" + Noise budget in fresh encryption: {0} bits",
decryptor.InvariantNoiseBudget(encryptedMatrix));
@ -74,7 +74,7 @@ namespace SEALNetExamples
Rotations require yet another type of special key called `Galois keys'. These
are easily obtained from the KeyGenerator.
*/
GaloisKeys galKeys = keygen.GaloisKeysLocal();
using GaloisKeys galKeys = keygen.GaloisKeysLocal();
/*
Now rotate both matrix rows 3 steps to the left, decrypt, decode, and print.
@ -82,7 +82,7 @@ namespace SEALNetExamples
Utilities.PrintLine();
Console.WriteLine("Rotate rows 3 steps left.");
evaluator.RotateRowsInplace(encryptedMatrix, 3, galKeys);
Plaintext plainResult = new Plaintext();
using Plaintext plainResult = new Plaintext();
Console.WriteLine(" + Noise budget after rotation: {0} bits",
decryptor.InvariantNoiseBudget(encryptedMatrix));
Console.WriteLine(" + Decrypt and decode ...... Correct.");
@ -130,27 +130,27 @@ namespace SEALNetExamples
{
Utilities.PrintExampleBanner("Example: Rotation / Rotation in CKKS");
EncryptionParameters parms = new EncryptionParameters(SchemeType.CKKS);
using EncryptionParameters parms = new EncryptionParameters(SchemeType.CKKS);
ulong polyModulusDegree = 8192;
parms.PolyModulusDegree = polyModulusDegree;
parms.CoeffModulus = CoeffModulus.Create(
polyModulusDegree, new int[] { 40, 40, 40, 40, 40 });
SEALContext context = new SEALContext(parms);
using SEALContext context = new SEALContext(parms);
Utilities.PrintParameters(context);
Console.WriteLine();
KeyGenerator keygen = new KeyGenerator(context);
PublicKey publicKey = keygen.PublicKey;
SecretKey secretKey = keygen.SecretKey;
RelinKeys relinKeys = keygen.RelinKeysLocal();
GaloisKeys galKeys = keygen.GaloisKeysLocal();
Encryptor encryptor = new Encryptor(context, publicKey);
Evaluator evaluator = new Evaluator(context);
Decryptor decryptor = new Decryptor(context, secretKey);
using KeyGenerator keygen = new KeyGenerator(context);
using PublicKey publicKey = keygen.PublicKey;
using SecretKey secretKey = keygen.SecretKey;
using RelinKeys relinKeys = keygen.RelinKeysLocal();
using GaloisKeys galKeys = keygen.GaloisKeysLocal();
using Encryptor encryptor = new Encryptor(context, publicKey);
using Evaluator evaluator = new Evaluator(context);
using Decryptor decryptor = new Decryptor(context, secretKey);
CKKSEncoder ckksEncoder = new CKKSEncoder(context);
using CKKSEncoder ckksEncoder = new CKKSEncoder(context);
ulong slotCount = ckksEncoder.SlotCount;
Console.WriteLine($"Number of slots: {slotCount}");
@ -168,12 +168,12 @@ namespace SEALNetExamples
Utilities.PrintLine();
Console.WriteLine("Encode and encrypt.");
Plaintext plain = new Plaintext();
using Plaintext plain = new Plaintext();
ckksEncoder.Encode(input, scale, plain);
Ciphertext encrypted = new Ciphertext();
using Ciphertext encrypted = new Ciphertext();
encryptor.Encrypt(plain, encrypted);
Ciphertext rotated = new Ciphertext();
using Ciphertext rotated = new Ciphertext();
Utilities.PrintLine();
Console.WriteLine("Rotate 2 steps left.");
evaluator.RotateVector(encrypted, 2, galKeys, rotated);

Просмотреть файл

@ -28,6 +28,7 @@ namespace SEALNetExamples
if (!Serialization.IsSupportedComprMode(ComprModeType.Deflate))
{
Console.WriteLine("ZLIB support is not enabled; this example is not available.");
Console.WriteLine();
return;
}
@ -53,7 +54,7 @@ namespace SEALNetExamples
*/
{
ulong polyModulusDegree = 8192;
EncryptionParameters parms = new EncryptionParameters(SchemeType.CKKS);
using EncryptionParameters parms = new EncryptionParameters(SchemeType.CKKS);
parms.PolyModulusDegree = polyModulusDegree;
parms.CoeffModulus = CoeffModulus.Create(
polyModulusDegree, new int[]{ 50, 20, 50 });
@ -134,7 +135,7 @@ namespace SEALNetExamples
we need to seek our stream back to the beginning.
*/
buffer.Seek(0, SeekOrigin.Begin);
EncryptionParameters parms2 = new EncryptionParameters();
using EncryptionParameters parms2 = new EncryptionParameters();
parms2.Load(buffer);
/*
@ -149,7 +150,7 @@ namespace SEALNetExamples
and creates the required keys.
*/
{
EncryptionParameters parms = new EncryptionParameters();
using EncryptionParameters parms = new EncryptionParameters();
parms.Load(parmsStream);
/*
@ -158,11 +159,11 @@ namespace SEALNetExamples
*/
parmsStream.Seek(0, SeekOrigin.Begin);
SEALContext context = new SEALContext(parms);
using SEALContext context = new SEALContext(parms);
KeyGenerator keygen = new KeyGenerator(context);
SecretKey sk = keygen.SecretKey;
PublicKey pk = keygen.PublicKey;
using KeyGenerator keygen = new KeyGenerator(context);
using SecretKey sk = keygen.SecretKey;
using PublicKey pk = keygen.PublicKey;
/*
We need to save the secret key so we can decrypt later.
@ -184,7 +185,7 @@ namespace SEALNetExamples
must be expanded before being used in computations; this is automatically
done by deserialization.
*/
Serializable<RelinKeys> rlk = keygen.RelinKeys();
using Serializable<RelinKeys> rlk = keygen.RelinKeys();
/*
Before continuing, we demonstrate the significant space saving from this
@ -192,7 +193,7 @@ namespace SEALNetExamples
*/
long sizeRlk = rlk.Save(dataStream);
RelinKeys rlkLocal = keygen.RelinKeysLocal();
using RelinKeys rlkLocal = keygen.RelinKeysLocal();
long sizeRlkLocal = rlkLocal.Save(dataStream);
/*
@ -214,14 +215,14 @@ namespace SEALNetExamples
*/
double scale = Math.Pow(2.0, 20);
CKKSEncoder encoder = new CKKSEncoder(context);
Plaintext plain1 = new Plaintext(),
plain2 = new Plaintext();
using Plaintext plain1 = new Plaintext(),
plain2 = new Plaintext();
encoder.Encode(2.3, scale, plain1);
encoder.Encode(4.5, scale, plain2);
Encryptor encryptor = new Encryptor(context, pk);
Ciphertext encrypted1 = new Ciphertext(),
encrypted2 = new Ciphertext();
using Encryptor encryptor = new Encryptor(context, pk);
using Ciphertext encrypted1 = new Ciphertext(),
encrypted2 = new Ciphertext();
encryptor.Encrypt(plain1, encrypted1);
encryptor.Encrypt(plain2, encrypted2);
@ -242,9 +243,9 @@ namespace SEALNetExamples
To use symmetric-key encryption, we need to set up the Encryptor with the
secret key instead.
*/
Encryptor symEncryptor = new Encryptor(context, sk);
Serializable<Ciphertext> symEncrypted1 = symEncryptor.EncryptSymmetric(plain1);
Serializable<Ciphertext> symEncrypted2 = symEncryptor.EncryptSymmetric(plain2);
using Encryptor symEncryptor = new Encryptor(context, sk);
using Serializable<Ciphertext> symEncrypted1 = symEncryptor.EncryptSymmetric(plain1);
using Serializable<Ciphertext> symEncrypted2 = symEncryptor.EncryptSymmetric(plain2);
/*
Before continuing, we demonstrate the significant space saving from this
@ -294,20 +295,20 @@ namespace SEALNetExamples
SEALContext and set up an Evaluator here.
*/
{
EncryptionParameters parms = new EncryptionParameters();
using EncryptionParameters parms = new EncryptionParameters();
parms.Load(parmsStream);
parmsStream.Seek(0, SeekOrigin.Begin);
SEALContext context = new SEALContext(parms);
using SEALContext context = new SEALContext(parms);
Evaluator evaluator = new Evaluator(context);
using Evaluator evaluator = new Evaluator(context);
/*
Next we need to load relinearization keys and the ciphertexts from our
dataStream.
*/
RelinKeys rlk = new RelinKeys();
Ciphertext encrypted1 = new Ciphertext(),
encrypted2 = new Ciphertext();
using RelinKeys rlk = new RelinKeys();
using Ciphertext encrypted1 = new Ciphertext(),
encrypted2 = new Ciphertext();
/*
Deserialization is as easy as serialization.
@ -319,7 +320,7 @@ namespace SEALNetExamples
/*
Compute the product, rescale, and relinearize.
*/
Ciphertext encryptedProd = new Ciphertext();
using Ciphertext encryptedProd = new Ciphertext();
evaluator.Multiply(encrypted1, encrypted2, encryptedProd);
evaluator.RelinearizeInplace(encryptedProd, rlk);
evaluator.RescaleToNextInplace(encryptedProd);
@ -345,23 +346,23 @@ namespace SEALNetExamples
In the final step the client decrypts the result.
*/
{
EncryptionParameters parms = new EncryptionParameters();
using EncryptionParameters parms = new EncryptionParameters();
parms.Load(parmsStream);
parmsStream.Seek(0, SeekOrigin.Begin);
SEALContext context = new SEALContext(parms);
using SEALContext context = new SEALContext(parms);
/*
Load back the secret key from skStream.
*/
SecretKey sk = new SecretKey();
using SecretKey sk = new SecretKey();
sk.Load(context, skStream);
Decryptor decryptor = new Decryptor(context, sk);
CKKSEncoder encoder = new CKKSEncoder(context);
using Decryptor decryptor = new Decryptor(context, sk);
using CKKSEncoder encoder = new CKKSEncoder(context);
Ciphertext encryptedResult = new Ciphertext();
using Ciphertext encryptedResult = new Ciphertext();
encryptedResult.Load(context, dataStream);
Plaintext plainResult = new Plaintext();
using Plaintext plainResult = new Plaintext();
decryptor.Decrypt(encryptedResult, plainResult);
List<double> result = new List<double>();
encoder.Decode(plainResult, result);

Просмотреть файл

@ -17,55 +17,73 @@ namespace SEALNetExamples
Utilities.PrintParameters(context);
Console.WriteLine();
EncryptionParameters parms = context.FirstContextData.Parms;
SmallModulus plainModulus = parms.PlainModulus;
using EncryptionParameters parms = context.FirstContextData.Parms;
using SmallModulus plainModulus = parms.PlainModulus;
ulong polyModulusDegree = parms.PolyModulusDegree;
Console.Write("Generating secret/public keys: ");
KeyGenerator keygen = new KeyGenerator(context);
using KeyGenerator keygen = new KeyGenerator(context);
Console.WriteLine("Done");
SecretKey secretKey = keygen.SecretKey;
PublicKey publicKey = keygen.PublicKey;
using SecretKey secretKey = keygen.SecretKey;
using PublicKey publicKey = keygen.PublicKey;
RelinKeys relinKeys = null;
GaloisKeys galKeys = null;
if (context.UsingKeyswitching)
{
/*
Generate relinearization keys.
*/
Console.Write("Generating relinearization keys: ");
timer = Stopwatch.StartNew();
relinKeys = keygen.RelinKeysLocal();
int micros = (int)(timer.Elapsed.TotalMilliseconds * 1000);
Console.WriteLine($"Done [{micros} microseconds]");
if (!context.KeyContextData.Qualifiers.UsingBatching)
Func<RelinKeys> GetRelinKeys = () => {
if (context.UsingKeyswitching)
{
Console.WriteLine("Given encryption parameters do not support batching.");
return;
/*
Generate relinearization keys.
*/
Console.Write("Generating relinearization keys: ");
timer = Stopwatch.StartNew();
RelinKeys result = keygen.RelinKeysLocal();
int micros = (int)(timer.Elapsed.TotalMilliseconds * 1000);
Console.WriteLine($"Done [{micros} microseconds]");
return result;
}
else
{
return null;
}
};
/*
Generate Galois keys. In larger examples the Galois keys can use a lot of
memory, which can be a problem in constrained systems. The user should
try some of the larger runs of the test and observe their effect on the
memory pool allocation size. The key generation can also take a long time,
as can be observed from the print-out.
*/
Console.Write($"Generating Galois keys: ");
timer = Stopwatch.StartNew();
galKeys = keygen.GaloisKeysLocal();
micros = (int)(timer.Elapsed.TotalMilliseconds * 1000);
Console.WriteLine($"Done [{micros} microseconds]");
}
Func<GaloisKeys> GetGaloisKeys = () => {
if (context.UsingKeyswitching)
{
if (!context.KeyContextData.Qualifiers.UsingBatching)
{
Console.WriteLine("Given encryption parameters do not support batching.");
return null;
}
Encryptor encryptor = new Encryptor(context, publicKey);
Decryptor decryptor = new Decryptor(context, secretKey);
Evaluator evaluator = new Evaluator(context);
BatchEncoder batchEncoder = new BatchEncoder(context);
IntegerEncoder encoder = new IntegerEncoder(context);
/*
Generate Galois keys. In larger examples the Galois keys can use a lot of
memory, which can be a problem in constrained systems. The user should
try some of the larger runs of the test and observe their effect on the
memory pool allocation size. The key generation can also take a long time,
as can be observed from the print-out.
*/
Console.Write($"Generating Galois keys: ");
timer = Stopwatch.StartNew();
GaloisKeys result = keygen.GaloisKeysLocal();
int micros = (int)(timer.Elapsed.TotalMilliseconds * 1000);
Console.WriteLine($"Done [{micros} microseconds]");
return result;
}
else
{
return null;
}
};
using RelinKeys relinKeys = GetRelinKeys();
using GaloisKeys galKeys = GetGaloisKeys();
using Encryptor encryptor = new Encryptor(context, publicKey);
using Decryptor decryptor = new Decryptor(context, secretKey);
using Evaluator evaluator = new Evaluator(context);
using BatchEncoder batchEncoder = new BatchEncoder(context);
using IntegerEncoder encoder = new IntegerEncoder(context);
/*
These will hold the total times used by each operation.
@ -108,7 +126,7 @@ namespace SEALNetExamples
into the polynomial. Note how the plaintext we create is of the exactly
right size so unnecessary reallocations are avoided.
*/
Plaintext plain = new Plaintext(parms.PolyModulusDegree, 0);
using Plaintext plain = new Plaintext(parms.PolyModulusDegree, 0);
timeBatchSum.Start();
batchEncoder.Encode(podValues, plain);
timeBatchSum.Stop();
@ -132,7 +150,7 @@ namespace SEALNetExamples
to hold the encryption with these encryption parameters. We encrypt
our random batched matrix here.
*/
Ciphertext encrypted = new Ciphertext(context);
using Ciphertext encrypted = new Ciphertext(context);
timeEncryptSum.Start();
encryptor.Encrypt(plain, encrypted);
timeEncryptSum.Stop();
@ -141,7 +159,7 @@ namespace SEALNetExamples
[Decryption]
We decrypt what we just encrypted.
*/
Plaintext plain2 = new Plaintext(polyModulusDegree, 0);
using Plaintext plain2 = new Plaintext(polyModulusDegree, 0);
timeDecryptSum.Start();
decryptor.Decrypt(encrypted, plain2);
timeDecryptSum.Stop();
@ -154,9 +172,9 @@ namespace SEALNetExamples
[Add]
We create two ciphertexts and perform a few additions with them.
*/
Ciphertext encrypted1 = new Ciphertext(context);
using Ciphertext encrypted1 = new Ciphertext(context);
encryptor.Encrypt(encoder.Encode(i), encrypted1);
Ciphertext encrypted2 = new Ciphertext(context);
using Ciphertext encrypted2 = new Ciphertext(context);
encryptor.Encrypt(encoder.Encode(i + 1), encrypted2);
timeAddSum.Start();
@ -286,53 +304,71 @@ namespace SEALNetExamples
Utilities.PrintParameters(context);
Console.WriteLine();
EncryptionParameters parms = context.FirstContextData.Parms;
using EncryptionParameters parms = context.FirstContextData.Parms;
ulong polyModulusDegree = parms.PolyModulusDegree;
Console.Write("Generating secret/public keys: ");
KeyGenerator keygen = new KeyGenerator(context);
using KeyGenerator keygen = new KeyGenerator(context);
Console.WriteLine("Done");
SecretKey secretKey = keygen.SecretKey;
PublicKey publicKey = keygen.PublicKey;
using SecretKey secretKey = keygen.SecretKey;
using PublicKey publicKey = keygen.PublicKey;
RelinKeys relinKeys = null;
GaloisKeys galKeys = null;
if (context.UsingKeyswitching)
{
/*
Generate relinearization keys.
*/
Console.Write("Generating relinearization keys: ");
timer = Stopwatch.StartNew();
relinKeys = keygen.RelinKeysLocal();
int micros = (int)(timer.Elapsed.TotalMilliseconds * 1000);
Console.WriteLine($"Done [{micros} microseconds]");
if (!context.KeyContextData.Qualifiers.UsingBatching)
Func<RelinKeys> GetRelinKeys = () => {
if (context.UsingKeyswitching)
{
Console.WriteLine("Given encryption parameters do not support batching.");
return;
/*
Generate relinearization keys.
*/
Console.Write("Generating relinearization keys: ");
timer = Stopwatch.StartNew();
RelinKeys result = keygen.RelinKeysLocal();
int micros = (int)(timer.Elapsed.TotalMilliseconds * 1000);
Console.WriteLine($"Done [{micros} microseconds]");
return result;
}
else
{
return null;
}
};
/*
Generate Galois keys. In larger examples the Galois keys can use a lot of
memory, which can be a problem in constrained systems. The user should
try some of the larger runs of the test and observe their effect on the
memory pool allocation size. The key generation can also take a long time,
as can be observed from the print-out.
*/
Console.Write($"Generating Galois keys: ");
timer = Stopwatch.StartNew();
galKeys = keygen.GaloisKeysLocal();
micros = (int)(timer.Elapsed.TotalMilliseconds * 1000);
Console.WriteLine($"Done [{micros} microseconds]");
}
Func<GaloisKeys> GetGaloisKeys = () => {
if (context.UsingKeyswitching)
{
if (!context.KeyContextData.Qualifiers.UsingBatching)
{
Console.WriteLine("Given encryption parameters do not support batching.");
return null;
}
Encryptor encryptor = new Encryptor(context, publicKey);
Decryptor decryptor = new Decryptor(context, secretKey);
Evaluator evaluator = new Evaluator(context);
CKKSEncoder ckksEncoder = new CKKSEncoder(context);
/*
Generate Galois keys. In larger examples the Galois keys can use a lot of
memory, which can be a problem in constrained systems. The user should
try some of the larger runs of the test and observe their effect on the
memory pool allocation size. The key generation can also take a long time,
as can be observed from the print-out.
*/
Console.Write($"Generating Galois keys: ");
timer = Stopwatch.StartNew();
GaloisKeys result = keygen.GaloisKeysLocal();
int micros = (int)(timer.Elapsed.TotalMilliseconds * 1000);
Console.WriteLine($"Done [{micros} microseconds]");
return result;
}
else
{
return null;
}
};
using RelinKeys relinKeys = GetRelinKeys();
using GaloisKeys galKeys = GetGaloisKeys();
using Encryptor encryptor = new Encryptor(context, publicKey);
using Decryptor decryptor = new Decryptor(context, secretKey);
using Evaluator evaluator = new Evaluator(context);
using CKKSEncoder ckksEncoder = new CKKSEncoder(context);
Stopwatch timeEncodeSum = new Stopwatch();
Stopwatch timeDecodeSum = new Stopwatch();
@ -374,7 +410,7 @@ namespace SEALNetExamples
from parms.
*/
double scale = Math.Sqrt(parms.CoeffModulus.Last().Value);
Plaintext plain = new Plaintext(parms.PolyModulusDegree *
using Plaintext plain = new Plaintext(parms.PolyModulusDegree *
(ulong)parms.CoeffModulus.Count(), 0);
timeEncodeSum.Start();
ckksEncoder.Encode(podValues, scale, plain);
@ -391,7 +427,7 @@ namespace SEALNetExamples
/*
[Encryption]
*/
Ciphertext encrypted = new Ciphertext(context);
using Ciphertext encrypted = new Ciphertext(context);
timeEncryptSum.Start();
encryptor.Encrypt(plain, encrypted);
timeEncryptSum.Stop();
@ -399,7 +435,7 @@ namespace SEALNetExamples
/*
[Decryption]
*/
Plaintext plain2 = new Plaintext(polyModulusDegree, 0);
using Plaintext plain2 = new Plaintext(polyModulusDegree, 0);
timeDecryptSum.Start();
decryptor.Decrypt(encrypted, plain2);
timeDecryptSum.Stop();
@ -407,10 +443,10 @@ namespace SEALNetExamples
/*
[Add]
*/
Ciphertext encrypted1 = new Ciphertext(context);
using Ciphertext encrypted1 = new Ciphertext(context);
ckksEncoder.Encode(i + 1, plain);
encryptor.Encrypt(plain, encrypted1);
Ciphertext encrypted2 = new Ciphertext(context);
using Ciphertext encrypted2 = new Ciphertext(context);
ckksEncoder.Encode(i + 1, plain2);
encryptor.Encrypt(plain2, encrypted2);
timeAddSum.Start();
@ -529,26 +565,35 @@ namespace SEALNetExamples
{
Utilities.PrintExampleBanner("BFV Performance Test with Degrees: 4096, 8192, and 16384");
EncryptionParameters parms = new EncryptionParameters(SchemeType.BFV);
using EncryptionParameters parms = new EncryptionParameters(SchemeType.BFV);
ulong polyModulusDegree = 4096;
parms.PolyModulusDegree = polyModulusDegree;
parms.CoeffModulus = CoeffModulus.BFVDefault(polyModulusDegree);
parms.PlainModulus = new SmallModulus(786433);
BFVPerformanceTest(new SEALContext(parms));
using (SEALContext context = new SEALContext(parms))
{
BFVPerformanceTest(context);
}
Console.WriteLine();
polyModulusDegree = 8192;
parms.PolyModulusDegree = polyModulusDegree;
parms.CoeffModulus = CoeffModulus.BFVDefault(polyModulusDegree);
parms.PlainModulus = new SmallModulus(786433);
BFVPerformanceTest(new SEALContext(parms));
using (SEALContext context = new SEALContext(parms))
{
BFVPerformanceTest(context);
}
Console.WriteLine();
polyModulusDegree = 16384;
parms.PolyModulusDegree = polyModulusDegree;
parms.CoeffModulus = CoeffModulus.BFVDefault(polyModulusDegree);
parms.PlainModulus = new SmallModulus(786433);
BFVPerformanceTest(new SEALContext(parms));
using (SEALContext context = new SEALContext(parms))
{
BFVPerformanceTest(context);
}
/*
Comment out the following to run the biggest example.
@ -558,7 +603,10 @@ namespace SEALNetExamples
//parms.PolyModulusDegree = polyModulusDegree;
//parms.CoeffModulus = CoeffModulus.BFVDefault(polyModulusDegree);
//parms.PlainModulus = new SmallModulus(786433);
//BFVPerformanceTest(new SEALContext(parms));
//using (SEALContext context = new SEALContext(parms))
//{
// BFVPerformanceTest(context);
//}
}
private static void ExampleBFVPerformanceCustom()
@ -580,7 +628,7 @@ namespace SEALNetExamples
string banner = $"BFV Performance Test with Degree: {polyModulusDegree}";
Utilities.PrintExampleBanner(banner);
EncryptionParameters parms = new EncryptionParameters(SchemeType.BFV)
using EncryptionParameters parms = new EncryptionParameters(SchemeType.BFV)
{
PolyModulusDegree = polyModulusDegree,
CoeffModulus = CoeffModulus.BFVDefault(polyModulusDegree)
@ -593,7 +641,11 @@ namespace SEALNetExamples
{
parms.PlainModulus = new SmallModulus(786433);
}
BFVPerformanceTest(new SEALContext(parms));
using (SEALContext context = new SEALContext(parms))
{
BFVPerformanceTest(context);
}
}
private static void ExampleCKKSPerformanceDefault()
@ -602,23 +654,32 @@ namespace SEALNetExamples
// It is not recommended to use BFVDefault primes in CKKS. However, for performance
// test, BFVDefault primes are good enough.
EncryptionParameters parms = new EncryptionParameters(SchemeType.CKKS);
using EncryptionParameters parms = new EncryptionParameters(SchemeType.CKKS);
ulong polyModulusDegree = 4096;
parms.PolyModulusDegree = polyModulusDegree;
parms.CoeffModulus = CoeffModulus.BFVDefault(polyModulusDegree);
CKKSPerformanceTest(new SEALContext(parms));
using (SEALContext context = new SEALContext(parms))
{
CKKSPerformanceTest(context);
}
Console.WriteLine();
polyModulusDegree = 8192;
parms.PolyModulusDegree = polyModulusDegree;
parms.CoeffModulus = CoeffModulus.BFVDefault(polyModulusDegree);
CKKSPerformanceTest(new SEALContext(parms));
using (SEALContext context = new SEALContext(parms))
{
CKKSPerformanceTest(context);
}
Console.WriteLine();
polyModulusDegree = 16384;
parms.PolyModulusDegree = polyModulusDegree;
parms.CoeffModulus = CoeffModulus.BFVDefault(polyModulusDegree);
CKKSPerformanceTest(new SEALContext(parms));
using (SEALContext context = new SEALContext(parms))
{
CKKSPerformanceTest(context);
}
/*
Comment out the following to run the biggest example.
@ -627,7 +688,10 @@ namespace SEALNetExamples
//polyModulusDegree = 32768;
//parms.PolyModulusDegree = polyModulusDegree;
//parms.CoeffModulus = CoeffModulus.BFVDefault(polyModulusDegree);
//CKKSPerformanceTest(new SEALContext(parms));
//using (SEALContext context = new SEALContext(parms))
//{
// CKKSPerformanceTest(context);
//}
}
private static void ExampleCKKSPerformanceCustom()
@ -649,12 +713,16 @@ namespace SEALNetExamples
string banner = $"CKKS Performance Test with Degree: {polyModulusDegree}";
Utilities.PrintExampleBanner(banner);
EncryptionParameters parms = new EncryptionParameters(SchemeType.CKKS)
using EncryptionParameters parms = new EncryptionParameters(SchemeType.CKKS)
{
PolyModulusDegree = polyModulusDegree,
CoeffModulus = CoeffModulus.BFVDefault(polyModulusDegree)
};
CKKSPerformanceTest(new SEALContext(parms));
using (SEALContext context = new SEALContext(parms))
{
CKKSPerformanceTest(context);
}
}
private static void ExamplePerformanceTest()

Просмотреть файл

@ -83,7 +83,7 @@ namespace SEALNetExamples
}
/*
Force a garbage collection after each example to accurately show memory pool use.
We may want to force a garbage collection after each example to accurately show memory pool use.
*/
GC.Collect();
}