Генерация пары ключей и шифрование данных с ее помощью в Mono C#

У меня есть модуль и показатель степени RSA, я хочу сгенерировать открытый ключ с этими компонентами. Затем я хочу зашифровать данные с помощью этого открытого ключа.

Итак, я написал эту функцию:

public static byte[] EncryptRSA(byte[] rsaModulus, byte[] exponent, byte[] data)
    {       
        byte[] response = null;
        RSACryptoServiceProvider rsa = new RSACryptoServiceProvider();
        RSAParameters rsaPar = rsa.ExportParameters(false);

        rsaPar.Modulus = rsaModulus;
        rsaPar.Exponent = exponent;

        rsa.ImportParameters(rsaPar);

        response = rsa.Encrypt(data, false);

        return response;
    }

но метод rsa.ExportParameters занимает много времени.

public RSACryptoServiceProvider ()
    : this (1024)
{
    // Here it's not clear if we need to generate a keypair
    // (note: MS implementation generates a keypair in this case).
    // However we:
    // (a) often use this constructor to import an existing keypair.
    // (b) take a LOT of time to generate the RSA keypair
    // So we'll generate the keypair only when (and if) it's being
    // used (or exported). This should save us a lot of time (at 
    // least in the unit tests).
}

Как видите, метод ExportParameters() выполняет генерацию пары ключей RSA, что требует много времени.

После этого я получаю исключение «Несоответствие закрытого/открытого ключа» при импорте параметров RSA.


person srdrgkcn89    schedule 14.05.2014    source источник
comment
Подсказка: private const bool PKCS1_1_5_PADDING = false; сделать код как минимум читабельным при вызове Encrypt.   -  person Maarten Bodewes    schedule 15.05.2014


Ответы (2)


Просто замените экспорт созданием нового объекта:

RSAParameters rsaPar = rsa.ExportParameters(false);

с

RSAParameters rsaPar = new RSAParameters();

Это все еще должно быть медленным в .net, но должно быть быстрым в моно, поскольку ключи создаются лениво.

Я также настоятельно рекомендую использовать заполнение OAEP вместо заполнения PKCS#1v1.5. У последнего есть слабые места, которые можно использовать на практике, если вы не будете тщательно их обходить. Так что используйте rsa.Encrypt(data, true), а не rsa.Encrypt(data, false).

person CodesInChaos    schedule 15.05.2014

Я не вижу четкого способа устранить тайм-аут, связанный с генерацией пары ключей. Вероятно, вам лучше использовать FromXMLString, так как я не вижу другого способа сгенерировать объект RSAParameters.

Что касается несоответствия, этого следовало ожидать — закрытый ключ все еще там. Microsoft использует второй RSACryptoServiceProvider (проверьте пример кода), чтобы обойти эту проблему.

person Maarten Bodewes    schedule 14.05.2014
comment
И, на мой взгляд, дизайнеры этого API требуют хорошего пинка. Они смешивают алгоритмы с ключами, открытыми и закрытыми ключами, кодированием/декодированием и чем-то еще. Неужели у них нет ни одного дизайнера, который повышает голос, когда видит такую ​​хрень? - person Maarten Bodewes; 15.05.2014
comment
Другим примером такого высокоуровневого дизайна является X509Certificate2 с его членом PrivateKey, который заставляет многих разработчиков .NET полагать, что подпись создается сертификатом :) Я думаю, что есть много людей, которым не нравится этот API, но, к сожалению, он, вероятно, никогда не получит изменены, потому что они хотят сохранить обратную совместимость. - person jariq; 16.05.2014