Szyfrowanie RSA

0

posiadam skrypt w javie który chciał bym przełożyć na C#, próbowałem swoich sił ale mi nie wychodzi, może wy mi pomożecie,

// Tworzenie kluczy KeyPairGenerator keygen = KeyPairGenerator.getInstance("RSA"); RSAKeyGenParameterSpec spec = new RSAKeyGenParameterSpec(1024, RSAKeyGenParameterSpec.F4); keygen.initialize(spec);

BigInteger publicKey = ((RSAPublicKey)keygen.generateKeyPair().getPublic()).getModulus();
// Tutaj wysyłam publiczny klucz do klienta który szyfruje dane i wysyła je serwerowi

// a tutaj serwer decryptuje dane
Cipher rsaCipher = Cipher.getInstance("RSA/ECB/nopadding");
rsaCipher.init(Cipher.DECRYPT_MODE, getClient().getRSAPrivateKey());
decrypted = rsaCipher.doFinal(_raw, 0x00, 0x80 );


ja zrobilem to tak:
<code class="c#">
// Tworzenie kluczy
this.Crypt = new RSACryptoServiceProvider(1024);
RSAParameters rsaPara = this.Crypt.ExportParameters(true);
rsaPara.Exponent = new byte[] { 1, 0, 1 }; // set Exponent to F4 = 65537
this.Crypt.ImportParameters(rsaPara);

this.PublicKey = this.Crypt.ExportParameters(false).Modulus;
// Tutaj wysyłam publiczny klucz do klienta który szyfruje dane i wysyła je serwerowi

// a tutaj serwer decryptuje dane
byte[] decrypted = this.Client.RSACrypt.Crypt.Decrypt(this.RawPacket, false);

i dostaje taki błąd przy próbie deszyfracji:

System.Security.Cryptography.CryptographicException: Złe dane.

   at System.Security.Cryptography.CryptographicException.ThrowCryptographicException(Int32 hr)
   at System.Security.Cryptography.RSACryptoServiceProvider.DecryptKey(SafeKeyHandle pKeyContext, Byte[] pbEncryptedKey, Int32 cbEncryptedKey, Boolean fOAEP, ObjectHandleOnStack ohRetDecryptedKey)
   at System.Security.Cryptography.RSACryptoServiceProvider.Decrypt(Byte[] rgb, Boolean fOAEP)

te skrypt pisany w javie działa idealnie, wiec musiałem coś sknocić ale nie mam pojęcia co :/

0

F4 to czwarta liczba fermata czyli miedzy dwoma jedynkami jest 15 zer ( 1 000000000000000 1 ). Ta liczba sluzy jako exponent, czyli w sumie to jest klucz publiczny.
rsaPara.Exponent = new byte[] { 1, 0, 1 }; - tu by bylo 1 00000000 1

zrob taki sami exponent jak jest to w javie zrobione, moze w tym lezy blad ktory odrzymales.

0

to ma być 1,0,1 ponieważ ten zbiór przekształcany jest na hext czyli 010001, jak wiadomo pierwsze zero odpada, i zostaje nam 10001, i potem program rozbija to na kod binarny, i mamy 10000000000000001, wiec to na pewno nie to.
a ja dalej nie mam pojęcia co z tym zrobić :/

//Edit
Z tego co widzę to najprawdopodobniej dzieje się tak przez to ze w javie jest nopadding, a z tego co widzę c# nie da się tego zrobić, macie jakieś propozycje?

//Edit 2
Skoro nikt nie wie, to będę musiał się zabrać za pisanie własnej klasy, ale do tego muszę dowiedzieć się co to jest "ECB" i czy nopadding oznacza po prostu brak tego "szyfrowania" bo to chyba jest szyfrowanie dodatkowe, muszę to wiedzie bo trzeba zaimplementować to: "RSA/ECB/nopadding"

Będę wdzięczny za każdą informacje

1

ECB to jest Electronic Code Book Mode. Czyli kazdy blok jest osobno szyfrowany, bez zadnych informacji z poprzedniego bloku. Innymi slowy jak masz jakis przypadkowy blok to mozesz go spokojnie rozszyfrowac i nie potrzebujesz miec wczesniejszych danych. ECB jest prostym i w sumie jest najniebezpieczniejszym trybem. Sa jeszcze: Cipher Block Chaining Mode (CBC) albo Output feedback (OFB)

0

Możesz skorzystać z gotowej biblioteki: http://www.bouncycastle.org/csharp/ - używałem kiedyś i bardzo sobie chwaliłem.

0

dzięki za odpowiedz, co do ECB nawet jeśli jest nie najlepszym rozwiązaniem muszę tak zrobić bo klient tego używa, i nie mam większego wyboru
a biblioteki http://www.bouncycastle.org/csharp/ już na paru forach widziałem ale one są bardzo obszerne a na stronie dużo wiadomości oprócz "fixow" NIE MA, jeśli jednak ty masz jakieś to z chęcią poczytam

//Edit
i mam jeszcze jedno pytanie, z tego co zauważalnym to ECB i padding to po prostu sposoby szyfrowania, czyli klucz RSA tworzy się zawsze tak samo, a tylko potem szyfruje i deszyfruje inaczej?
Jeśli tak to zaoszczędziło by mi to roboty bo mógł bym stworzyć klucz za pomocą gotowych klas a sam zrobić tylko szyfrowanie i deszyfracje.

1
varens napisał(a)

//Edit
i mam jeszcze jedno pytanie, z tego co zauważalnym to ECB i padding to po prostu sposoby szyfrowania, czyli klucz RSA tworzy się zawsze tak samo, a tylko potem szyfruje i deszyfruje inaczej?
Jeśli tak to zaoszczędziło by mi to roboty bo mógł bym stworzyć klucz za pomocą gotowych klas a sam zrobić tylko szyfrowanie i deszyfracje.

RSACryptoServiceProvider stworzy Ci klucze w postaci kilkuset cyfrowych liczb. Możesz ich użyć we własnej metodzie szyfrującej i deszyfrującej, nie musisz pisać metody do ich generowania.

0

nom, dzięki za odpowiedz ale już przetestowałem to wczoraj na moim skrypcie i działa ;]
po prostu RSACryptoServiceProvider tworzy mi klucze, a ja dorobiłem metodę do szyfrowania/deszyfrowania "RSA/ECB/nopadding"

PS.
Dzięki za wszystkie odpowiedzi, bardzo mi się przydały

1 użytkowników online, w tym zalogowanych: 0, gości: 1