Внедрить безопасную связь с использованием шифрования RSA в C # - PullRequest
1 голос
/ 23 марта 2012

Я хочу реализовать сценарий, в котором две конечные точки могут безопасно обмениваться данными друг с другом с использованием шифрования с открытым / закрытым ключом.Сценарий следующий:

Для того, чтобы A отправил сообщение B:

A зашифровывает сообщение, используя закрытый ключ А.

A шифрует сообщение с использованием открытого ключа B.

A отправляет сообщение.

B получает сообщение.

B расшифровывает сообщение, используя открытый ключ A.

B расшифровывает сообщение, используя закрытый ключ B.

B читает сообщение.

Вот что у меня есть в C # с использованием шифрования RSA:

// Alice wants to send a message to Bob:

String plainText = "Hello, World!";
Byte[] plainData = Encoding.Default.GetBytes(plainText);
Byte[] cipherData = null;

RSACryptoServiceProvider alice = new RSACryptoServiceProvider();
RSACryptoServiceProvider bob = new RSACryptoServiceProvider();

var alicePrivateKey = alice.ExportParameters(true);
var alicePublicKey = alice.ExportParameters(false);

var bobPrivateKey = bob.ExportParameters(true);
var bobPublicKey = bob.ExportParameters(false);

RSACryptoServiceProvider messenger = new RSACryptoServiceProvider();

messenger.ImportParameters(alicePrivateKey);
cipherData = messenger.Encrypt(plainData, true);

messenger.ImportParameters(bobPublicKey);
cipherData = messenger.Encrypt(cipherData, true);

messenger.ImportParameters(alicePublicKey);
cipherData = messenger.Decrypt(cipherData, true);

messenger.ImportParameters(bobPrivateKey);
cipherData = messenger.Decrypt(cipherData, true);            

String result = Encoding.Default.GetString(alice.Decrypt(cipherData, true));

Понятно, что что-то не так со следующими строками:

messenger.ImportParameters(bobPublicKey);
cipherData = messenger.Encrypt(cipherData, true);

, который выдает System.Security.Cryptography.CryptographyException с сообщением {"Bad Length"} .

Как я вижу, он не может зашифровать данные, используя только открытую часть ключа Боба.

Может кто-нибудь пролить свет на то, как правильно выполнить то, что яхочу сделать в C # ?

Ответы [ 2 ]

4 голосов
/ 23 марта 2012

Здесь две проблемы:

A) Ваш протокол протекает неправильно.Если вы хотите использовать RSA для обмена сообщениями, алгоритм таков:

Зашифровывает сообщение, используя B public key

A, отправляет сообщение

B расшифровывает сообщение, используя личный ключ B

(B выполняет обработку)

B шифрует сообщение, используя открытый ключ A

B отправляет сообщение

A, расшифровывает сообщение, используя личный ключ

и т. Д.Обратите внимание, что A не знает закрытый ключ B, и наоборот.Открытый и закрытый ключи связаны таким образом, что сообщение, зашифрованное открытым ключом (известным каждому), может быть расшифровано только с соответствующим закрытым ключом (известным только получателю зашифрованного сообщения).В этом-то и весь смысл RSA.

Что касается реализации в C #, то сделать с классами Crypto довольно просто, когда вы действительно поймете основные концепции.См., Например, здесь и здесь .

B) RSA подходит для обмена небольшими объемами данных.Он предназначен для обмена ключами по небезопасному каналу без необходимости использования общего секрета.Для обмена «нормальными» данными используется симметричный алгоритм, такой как AES.Таким образом, идея состоит в том, чтобы сгенерировать случайную фразу-пароль и IV из A и отправить ее B через RSA, как обсуждалось в A;после того, как обе стороны знают кодовую фразу и IV, они могут просто зашифровать данные, используя AES с общим ключом.

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

1 голос
/ 23 марта 2012

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

Для получения дополнительной информации вы можете обратиться к этому вопросу: как использовать RSA для шифрования файлов (огромных данных) в C #

...