JavaでOpenSSLによって生成されたRSAパブリックおよび秘密鍵を使用したデータ暗号化と復号化
RSAとは:RSA公開キー暗号化アルゴリズムは、1977年にRon Rivest、Adi Shamirh、およびLen Adleman at(Massachusetts Institute of Technology)によって開発されました。 RSAネーミングは、それらの3つを開発する名前から来ています。 RSAは、現在最も影響力のある公開キー暗号化アルゴリズムです。これまで知られているすべての暗号攻撃に抵抗することができ、ISOは公開キーデータ暗号化標準として推奨されています。現在、この暗号化方法は、オンラインバンキング、デジタル署名、その他の機会で広く使用されています。 RSAアルゴリズムは非常にシンプルな数の理論の事実に基づいています。2つの大きな素数を掛けるのは非常に簡単ですが、当時製品を考慮することは非常に困難であるため、製品を暗号化キーとして開示できます。
OpenSSLとは:多数の暗号化アルゴリズム、公開キーインフラストラクチャ標準、およびSSLプロトコル、およびおそらくこれらの興味深い機能により、これらすべてのアルゴリズムと標準を実装するというアイデアが得られます。もしそうなら、あなたの賞賛を表明しながら、私はまだあなたに思い出させずにはいられません:これは困難なプロセスです。この作業は、いくつかの暗号モノグラフやプロトコルドキュメントを読むほど簡単ではなく、これらすべてのアルゴリズム、標準、プロトコルドキュメントのすべての詳細を理解し、これらの定義とプロセスを1つずつ実装して、よく知っているキャラクターを使用します。この楽しくてひどい仕事をするのにどれだけの時間が必要かはわかりませんが、それは確かに1年か2年の問題ではありません。 OpenSSLは、1995年以来、2人の偉大な男性、エリックA.ヤングとティムJ.ハドソンによって書かれた多くのセキュリティアルゴリズムを組み合わせたアルゴリズムコレクションです。コマンドまたは開発ライブラリを通じて、標準のパブリックアルゴリズムアプリケーションを簡単に実装できます。
私の仮説的なアプリケーションの背景の1つ:
モバイルインターネットの人気により、モバイルデバイス向けに開発されたアプリケーションが次々と出現しています。これらのアプリケーションには、多くの場合、ユーザー登録とパスワード検証機能が伴います。 「ネットワーク伝送」と「アプリケーションログアクセス」には、セキュリティに隠された危険があります。パスワードはユーザーにとって敏感なデータであり、開発者はアプリケーションが起動する前にセキュリティ上の予防策を講じる必要があります。不適切な取り扱いは、ビジネス競合他社による悪意のある攻撃や、サードパーティのパートナーによる訴訟などの問題を引き起こす可能性があります。
RSAアルゴリズムには非常に多くの利点がありますが、インターネット上にそれらを操作する方法を説明する完全な例はありません。以下に紹介させてください。
1. OpenSSLを使用して、プライベートキーとパブリックキーを生成します
Linuxシステムを使用しており、OpenSSLパッケージをインストールしています。 OpenSSLがマシンにインストールされていることを確認してください。コマンドを実行するときは、次の情報が表示されます。
[root@chaijunkun〜]#opensSlバージョン-a opensSl 1.0.0 -fips 29 2010年3月29日ビルド:水曜日25:17:15 GMT 2012プラットフォーム:Linux -x86_64オプション:BN(64,64)MD2(64,64)MD2(INT)RC4(16X、INT)DES(IDX、16、BlowPINCE) -DOPENSSL_PIC -DZLIB -DOPENSSL_THREADS -D_REENTRANT -DDSO_DLFCN -DHAVE_DLFCN_H -DKRB5_MIT -M64 -DL_ENDIAN -DERTIAN -DERTY -WALL -O2 -G -PIPE -WALL -WALL -WALL -WALL -WALL -WALL -param = ssp -buffer -size = 4 -m64 -mtune = gentune -wa、-noexecstack -dmd32_reg_t = int -dopenssl_ia32_sse2 -dopenssl_bn_asm_mont -dsha1_asm -dsha256_asm -dsha512_asm_asm_asm_asm_asm_asm_asm -dwhirlpool_asm openssldir: "/etc/pki/tls"エンジン:aesni dynamic
最初に秘密鍵を生成します:
[root@chaijunkun〜]
このコマンドにより、OpenSSLは秘密鍵をランダムに生成でき、暗号化の長さは1024ビットです。暗号化された長さとは、許可された最大「暗号化された情報」の長さの理論的制限、つまりプレーンテキストの長さの制限を指します。このパラメーターが増加すると(たとえば、2048)、許容される平文の長さも増加しますが、コンピューティングの複雑さも急速に増加します。推奨される長さは1024ビット(128バイト)です。
秘密鍵のコンテンツを見てみましょう:
[root@chaijunkun〜] mcydt1xr/t2ahgoixnq5v8w4icaaenawi7ajarhtvx1uoh/2u378fsceeseg8xdq ll0gcfb1/tjki2aitvszxotrs8kyggu78f7vvmdngxilk3gdhnzh+uoeqywidaqab aogaaekk76cssp7k90mwywp18ghlzru+vehft9bpv67cglg1owfbntfyqspvstfm u2lwn5hd/egaj4folxdm43kt4wyznoabszzckkxs6urciu8nqafnoabszckxsdm43kt4wyznoabszck phu2te7vi4ldkw9df1fya+dscslnadaun3ohb55jqgl+ls5ecqqdufuxxn3uqgykkkkkkkkkkxbjnanapcq71szjqam777r3wilkfh933333333333333333333333333333333333333333333333333333333333333333333333333333333330H9IIV0ACQC4J ihysll9lakeawgh4jxxxxxeiaufmsgjoi3qpjqgvumkx0w96mcpcwv3fsew7w1/msi sutkjp5bbvvjfvfwfwfmahyljdp7w+nebwkbwjaybz/eb5naza4pxbr5vmcd8aj4 egplwsji/mkhrb484xz2vyuiciwywnmfxpa3ydgqwskqdgy3rll9lv8/aqjacjli ifigur ++ njxa8c4xy0czsobj76k710wde1mpgr5wgqf1t+P /ybxbd16qvixjvnt6qjabli6zx9gyrwnu6akpdahd8qjwonnnfnlqhue4wepevkm cysg+ibs2ggsxntrzlwjlfx7vhmpqtnttc8ynmx1kfw = ------- end rsa prive key-------------
内容はすべて標準的なASCII文字であり、最初とエンディングラインに明らかなマークがあり、実際の秘密鍵データは中央の不規則な文字です。
補足2015年3月24日:キーファイルは、最終的にBase64エンコーディングを介してデータを保存します。上記のキーファイルコンテンツの各行の長さが非常に規則的であることがわかります。これは、RFC2045の規定によるものです。エンコードされた出力ストリームは、それぞれ76文字以下の行で表す必要があります。つまり、base64によってエンコードされたデータは、1行あたり76文字を超えることはなく、超長データのためにrowで分割する必要があります。
次に、秘密鍵に基づいて公開キーを生成します。
[root@chaijunkun〜]
公開鍵の内容を見てみましょう。
[root@chaijunkun〜] /umxx2jk6qeen69t6n2r1i/lmcydt1xr/t2ahgoixnq58w4icaaenawi7ajarht vx1uoh/2u378fsceeseg8xdql0gcfb1/tjki2aitvszotrs8kggu78f7f7f7f7f7f7f78f xilk3gdhnzh+uoeqywidaqab ----エンド公開キー----
現時点では、秘密鍵を直接使用できないため、PKCS#8エンコーディングが必要です。
[root@chaijunkun〜]
コマンドは、入力秘密キーファイルがrsa_private_key.pemであり、出力の秘密キーファイルがpkcs8_rsa_private_key.pemであり、二次暗号化は使用されないことを示しています(-nocrypt)
エンコードされた秘密キーファイルが以前の秘密キーファイルと異なるかどうかを見てみましょう。
[root@chaijunkun〜]#cat pkcs8_rsa_private_key.pem
-----秘密鍵を開始----- MiicdQibadanbgkkhkig9w0baqefaascal8wggjbageaaogbakepnypd+taaxcfg 6dsqnv/h7zd9szfhaotqoqsfr23o3zhwl8uzzinpxgv9pyacy6jc1dlxxxbiijpp4 1RCLTOLPGG1XHW44F/ZTFVX+XWQRIQBXCOQWXQYJ8HX9OMOJZQK1VLNC61GZYRIA ZTVX/TWYM2BCIWTEB2GFOH66GGRDLAGMBAAECGYBP4QTVOJKYNUT3SBDJY/XWACGYBP4QTVOJKYNUT3SBDJY/XWA U768SF9P0GLXRTWYUDWJAVUE0VHBI9WXTAVAFKCP8HXX4QZQZQPH84TD0ZJCQ3J DLOEGAFJKIORGZQ5FYK7YDBOU1TLJFV459C8DTZMTU+LGSOTD11/V/V/V/V/V/V/V/V/V/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/v/vs MBQ3C4CHMOOYV4UZKQJBANR+7FC3E6OZGQTOESQPSPQLJBSDF9E4X4EDFUOECKKKJ DVVLOOOAZVTHFAIUP+H3FK4HXRPALINBEIDHIIUX2UCQQDCCHIPHFD4G58YYCM 6leqkmoa+6ypfrb3b3oxyklbxcwx7dtbx+ayky5oqmnkeg+mw8xb8wadiul0/tb6cq farvakbhvp94hk0dmdinfvhlwyj3xy4pongsa8vcymj+asgtvjzjfnzxk4gjfnzxk4gjfjfnzxk4g4gJfjjfjjfjjfjjfjjbjj 2Z9EKDFIOBBAWQP2DLDGUX2VXZ8BAKBYMUIH+KBSV76CNEDWLHFLQJLKGENVQTVX TB0TUW8AVLABAXW34/5SI+NUB1HMBGHTYK/T/IFCEPXPBWLGO+E3PAKWLPNHH0ZH fae7oaqkmad3xcny6ec180tae57hz6ks+sylkwb4ggzyacxc22vmtyksxhtueamo 1nmlzi2zfuox -----エンド秘密鍵-----
この時点で、利用可能なキーペアが生成されました。秘密鍵はPKCS8_RSA_PRIVATE_KEY.PEMを使用し、公開キーはrsa_public_key.pemを使用します。
2014年5月20日に追加された:最近、RSA暗号化の必要性に遭遇しました。他の当事者は、最初のステップで生成されたPKCS#8によってエンコードされていない秘密キーファイルのみを使用できることを要求しました。その後、関連するドキュメントを確認し、最初のステップで生成された秘密キーファイルがPKCS#1形式であることを知りました。この形式は実際にはJavaによってサポートされていますが、さらに2行のコードを書きます。
rsaprivateKeyStructure asn1privkey = new rsaprivatekeyStructure((asn1 sequence)asn1 sequence.frombytearray(prikeydata)); rsaprivatekeyspec rsaprivkeyspec = new rsaprivatekeyspec(asn1privkey.getModulus()、asn1privkey.getPrivateExponent()); KeyFactory keyFactory = keyFactory.getInstance( "rsa"); privatekey prikey = keyfactory.generetprivate(rsaprivkeyspec);
最初にPKCS#1の秘密キーファイルを読み取り(マイナス記号の先頭にコメントコンテンツを削除することに注意してください)、次にbase64を使用して読み取り文字列をデコードして、コードの最初の行のパラメーターであるprikeydataを取得します。最後の行は秘密鍵を取得します。次の使用法に違いはありません。
参照:https://community.oracle.com/thread/1529240?start=0&tstart=0
2。Javaコードを書いてテストします
補足2012年2月23日:標準JDKはJCEでのみ指定されています(JCE(JAVA暗号化拡張)は、暗号化、キー生成およびネゴシエーション、およびメッセージ認証コード(MAC)アルゴリズムのフレームワークと実装を提供するパッケージのセットです。対称、吸気、吸収団体のサポートをサポートするためのエンクレーションサポートを提供します。インターフェイスですが、内部実装は、ここではBouncycastleのオープンソースJCE実装パッケージを使用する必要がありますJDKバージョンでは、前のダウンロードページで対応するバージョンを見つけることができます。
私が実装したコードを見てみましょう。
パッケージnet.csdn.blog.chaijunkun; java.io.bufferedreaderをインポートします。 java.io.ioexceptionをインポートします。 java.io.inputStreamをインポートします。 java.io.inputStreamReaderをインポートします。 java.security.invalidkeyexceptionをインポートします。 java.security.keyfactoryをインポートします。 java.security.keypairをインポートします。 java.security.keypairgeneratorをインポートします。 java.security.nosuchalgorithmexceptionをインポートします。 java.security.securerandomをインポートします。 java.security.interfaces.rsaprivatekeyをインポートします。 java.security.interfaces.rsapublickeyをインポートします。 Java.security.spec.invalidkeyspecexceptionをインポートします。 java.security.spec.pkcs8encodedkeyspecをインポートします。 java.security.spec.x509encodedkeyspecをインポートします。 javax.crypto.badpaddingexceptionをインポートします。 javax.crypto.cipherをインポートします。 javax.crypto.illegalblocksizeexceptionをインポートします。 javax.crypto.nosuchpaddingexceptionをインポートします。 org.bouncycastle.jce.provider.bouncycastleproviderをインポートします。 sun.misc.base64decoderをインポートします。 public class rsaencrypt {private static final string default_public_key = "migfma0gsqgsib3dqebaquaa4gnadcbiqkbgqchdzcjw/rwgfwnxunbkp7/4e8w" + "/r" + " +" + "/umxx2jk6qeen69t6n2r1i/lmcydt1xr/t2ahgoixnq58w4icaaenawi7ajarht" + "/r" + "vx1uoh/2u378fsceeSeg8xdql0gcfb1/tjki2aitvsxxxxotrs88ugguggugggggggggggggggggggggg "/r" + "xilk3gdhnzh + uoeqywidaqab" + "/r";プライベート静的最終文字列default_private_key = "miicdqibadanbgkqhkig9w0baqefaascal8wggjbageaaogbakepnypd + taaxcfg" + "/r" + "6DSQNV/H7ZD9SZFHAOTQOQSFR23O3ZHWL8UZZINPXGV9PYACY6JC1DLXXBIIJPP4" + "/r" + "1rcltolpgg1xhw44f/ztfvx + xwqriqbxcoqwxqyj8hx9omojzqk1vlnc61gzyria" + "/r" + "ztvx/twym2bciwteb2gfoh66666gragmbaaecgybp4qtvojkynut3sbdjy/xwaetm" + "/r" + "U768SF9P0GLXRTWYUDWJAVUE0VHBI9WXMWZTAVAFKCP8HXX4QZQPH84TD0ZJCQ3J" + "/r" + "dloegafjkiorgzq5fyk7ydbou1tljfv459c8dtzmtu + lgsotd11/v/jr4njxiudo" + "/r" + "mbq3c4chmooyv4uzkqjbanr + 7fc3e6ozgtppqljbsfuctdfcdfuctdfcdfuctfuectfuctpljbbuctfuctpljbbuctpljbbuctfuctpljbbuctpljbuctplJ + "/r" + "dvvloooazvthfaiup + h3fk4hxrpalinbeinbeidhiux2ucqqdcchiphfd4gc58yycm" + "/r" + "6leqkmoa+6ypfrb3oxyklbxcwx7dtbx+ayky5oqmnkeg+mw8xb8wadiul0/tb6cq"+"/r"+ "FARVAKBHVP94HK0DMDINFVHLWYJ3XY4PONGSA8VCYMJ + ASGTVJZJFNZXK4GIJBJA" + "/r" + "2Z9EKDFIOBBAWQP2DLDGUX2VXZ8BAKBYMUIH + KBSV76CNEDCHENDFLQMUIHIH "/r" + "TB0TUW8AVLABAXW34/5SI + NUB1HMBGYTK/T/IFCEPXPBWLGO + E3PAKAGWLPNH0ZH" + "/r" + 「fae7oaqkmad3xcny6ec180tae57hz6ks + sylkwb4ggzyacxc22vmtyksxhtueamo " +"/r " +" 1nmlzi2zfuox " +"/r "; / *** private key*/ private rsaprivatekey privatekey; / ***公開キー*/ private rsapublickey publickey; / *** stringにプライベートセット*/ private static final char [] hex_char = {'0'、 '1'、 '2'、 '3'、 '4'、 '5'、 '6'、 '7' 8 '、' 9 '、'、 'b'、 'c'、 'd'、 'e' f '}; / ***秘密鍵を取得* @return現在の秘密キーオブジェクト*/ public rsaprivatekey getPrivateKey(){return privatekey; } / ***公開キーを取得* @return現在の公開キーオブジェクト* / public rsapublickey getpublickey(){return publickey; } / ***ランダムに生成されたキーペア* / public void genkeypair(){keypairgenerator keypairgen = null; try {keypairgen = keypairgenerator.getInstance( "rsa"); } catch(nosuchalgorithmexception e){e.printstacktrace(); } keypairgen.initialize(1024、new Securerandom()); keypair keypair = keypairgen.generatekeypair(); this.privatekey =(rsaprivatekey)keypair.getPrivate(); this.publickey =(rsapublickey)keypair.getPublic(); } / ***ファイルの入力ストリームから公開キーをロードします* @param in public key input stream* @throws例外例外鍵をロードするときに生成されます* / public void loadpublickey(inputstream in)throws {try {bufferedreader br = new inputstreamreader(in in);文字列readline = null; stringbuilder sb = new StringBuilder(); while((readline = br.readline())!= null){if(readline.charat(0)== ' - '){contion; } else {sb.append(readline); sb.append( '/r'); }} loadpublickey(sb.toString()); } catch(IOException e){新しい例外をスロー( "Public Data Stream Read Error"); } catch(nullpointerexception e){新しい例外をスロー( "public key inputストリームは空です"); }} / ***文字列から公開キーをロードする* @param publickeystr public key data string* @throws exception exception exception excements excuned with with wish cobuly key* / public void loadpublickey(string publickeystr)throws {try {base64decoder base64decoder = new base64decoder( byte [] buffer = base64decoder.decodebuffer(publicKeystr); KeyFactory keyFactory = keyFactory.getInstance( "rsa"); X509ENCODEDKEYSPEC KEYSPEC = new X509ENCODEDKEYSPEC(バッファー); this.publickey =(rsapublickey)keyFactory.generepublic(keyspec); } catch(nosuchalgorithmexception e){throw new Exception( "Nothing algorithm"); } catch(invalidkeyspecexception e){新しい例外をスロー( "public Key Illegal"); } catch(ioException e){新しい例外をスロー( "公開キーデータコンテンツ読み取りエラー"); } catch(nullpointerexception e){新しい例外をスロー( "public key data is vealt"); }} / ***ファイルから秘密鍵をロード* @param keyfilename private key file name* @returnが成功したかどうか* @throws例外* / public void loadprivatekey(inputstream in)throws {try {bufferedreader br = new inputstreamreader(new inputstreamreader(in));文字列readline = null; stringbuilder sb = new StringBuilder(); while((readline = br.readline())!= null){if(readline.charat(0)== ' - '){contion; } else {sb.append(readline); sb.append( '/r'); }} loadprivatekey(sb.toString()); } catch(ioException e){新しい例外をスロー( "秘密キーデータ読み取りエラー"); } catch(nullpointerexception e){新しい例外をスロー( "秘密キー入力ストリームは空です"); }} public void loadprivatekey(string privatekeystr)スロー例外{try {base64Decoder base64Decoder = new base64Decoder(); byte [] buffer = base64decoder.decodebuffer(privatekeystr); pkcs8encodedkeyspec keyspec = new pkcs8encodedkeyspec(buffer); KeyFactory keyFactory = keyFactory.getInstance( "rsa"); this.privatekey =(rsaprivatekey)keyfactory.generepprivate(keyspec); } catch(nosuchalgorithmexception e){新しい例外をスロー( "Nothing this algorithm"); } catch(invalidkeyspecexception e){新しい例外をスロー( "秘密鍵違法"); } catch(ioException e){新しい例外をスロー( "秘密キーデータコンテンツ読み取りエラー"); } catch(nullpointerexception e){新しい例外をスロー( "秘密キーデータは空"); }} / ***暗号化プロセス* @param publickey公開鍵* @param plaintextdata plaintext data* @throws例外情報暗号化プロセス中* / public byte [] encrypt(rsapublickey publickey、byte [] byte [] plaintextdata)スロー例外{public = = null) } cipher cipher = null; try {cipher = cipher.getInstance( "rsa"、new bouncastleprovider()); cipher.init(cipher.encrypt_mode、publickey); byte [] output = cipher.dofinal(plaintextdata);返品出力; } catch(nosuchalgorithmexception e){新しい例外をスロー( "nothis暗号化アルゴリズム"); } catch(nosuchpaddingexception e){e.printstacktrace(); nullを返します。 } catch(invalidKeyException e){新しい例外をスロー( "暗号化公開キーは違法です、確認してください"); } catch(Illegalblocksizeexception e){新しい例外をスロー( "PlackText Length is Illegal"); } catch(badPaddingException e){新しい例外をスロー( "PlackTextデータが破損している"); }} / *** decryption Process* @param privatekey private key* @param cipherdata ciphertext data* @return plaintext* @throws例外情報* / public byte [] decrypt(rsaprivatekey privatekey、byte [] cipherdata [] cipherdata) セット"); } cipher cipher = null; try {cipher = cipher.getInstance( "rsa"、new bouncastleprovider()); cipher.init(cipher.decrypt_mode、privatekey); byte [] output = cipher.dofinal(cipherdata);返品出力; } catch(nosuchalgorithmexception e){新しい例外をスロー( "Nothing Decryption algorithm"); } catch(nosuchpaddingexception e){e.printstacktrace(); nullを返します。 } catch(invalidKeyException e){新しい例外をスロー( "decryption秘密キーは違法です、確認してください"); } catch(Illegalblocksizeexception e){新しい例外をスロー( "cryptotextの長さは違法です"); } catch(badPaddingException e){新しい例外をスロー( "CryptoTextデータが破損している"); }} / *** hexadecimal stringへのバイトデータ* @paramデータ入力データ* @return hexadecimal content* / public static string bytearraytostring(byte [] data){stringbuilder stringbuilder = new StringBuilder(); for(int i = 0; i <data.length; i ++){//バイトの高4桁をインデックスとして取り出して、対応する16進数の識別子を取得して、符号なしの右シフトstringbuilder.append((data [i]&0xf0)>> 4]); //インデックスとしてバイトの下部4ビットを取り出して、対応するヘキサデシマル識別子stringbuilder.append(hex_char [(data [i]&0x0f)))を取得します。 if(i <data.length-1){stringbuilder.append( ''); }} return stringbuilder.toString(); } public static void main(string [] args){rsaencrypt rsaencrypt = new rsaencrypt(); //rsaencrypt.genkeypair(); //公開キーをロードしてください{rsaencrypt.loadpublickey(rsaencrypt.default_public_key); system.out.println( "公開キーのロードに正常に"); } catch(Exception e){System.err.println(e.getMessage()); System.err.println( "公開キーのロードに失敗した"); } //秘密キーのロード{rsaencrypt.loadprivatekey(rsaencrypt.default_private_key); System.out.println( "秘密鍵のロードに正常に"); } catch(Exception e){System.err.println(e.getMessage()); system.err.println( "秘密キーの読み込み障害"); } // test string string encryptstr = "test string chaijunkun"; try {// byte [] cipher = rsaencrypt.encrypt(rsaencrypt.getPublickey()、encryptstr.getBytes()); // decrypt byte [] plantext = rsaencrypt.decrypt(rsaencrypt.getPrivateKey()、cipher); system.out.println( "ciphertext length:"+ cipher.length); system.out.println(rsaencrypt.bytearraytostring(cipher)); System.out.println( "Plantext length:"+ plaintext.length); system.out.println(rsaencrypt.bytearraytostring(plantext)); System.out.println(new String(Plantext)); } catch(Exception e){System.err.println(e.getMessage()); }}}コードでは、パブリックキーとプライベートキーをロードする2つの方法を提供します。
Stream By Read:AndroidアプリケーションでのIDインデックスリソースによってInputStreamを取得する方法に適しています。
文字列で読む:コードに示されているように、キーコンテンツを線で静的定数に保存し、文字列ごとにキーをインポートします。
上記のコードを実行すると、次の情報が表示されます。
1 64 57 C8 E3 46 A7 CE 57 31 AC CD 21 89 89 8F C1 24 C1 22 0C CB 70 6A 0D FA C9 38 80 BA 2E E1 29 02 ED 45 9E 88 E9 23 09 87 AF AD AB AC CB 61 03 3C A1 81 56 A5 D C4 79 A5 A5 55 555 5 9f Fd 22 87 9e de b1 f4 e8 b2平野テキスト長:22 54 65 73 74 20 53 74 72 69 6e 67 20 63 68 61 69 6a 75 6e 6b 75 6e Test String Chaijunkun
主な関数では、「rsaencrypt.genkeypair()」をコメントしました。これは、キーペアをランダムに生成するために使用されます(生成、使用、保存ではなく)。ファイルキーが使用されていない場合、キーをロードするコードにコメントしたり、このメソッドを有効にしたり、コードを実行したりできます。
公開キーのロードと秘密鍵のロードの違いは、公開キーがロードされたとき、x509EncodedKeyspec(x509エンコードキー命令)、および秘密鍵がロードされると、pkcs8encodedkeyspec(pkcs#8がエンコードされたキー命令)をロードすることです。
2012年2月22日に追加:Androidソフトウェアの開発中に、上記のコードが適切に機能しないことがわかりました。主な理由は、sun.misc.base64decoderクラスがAndroid開発パッケージに存在しないことです。したがって、インターネット上でRt.Jarのソースコードを探す必要があります。 JDKのsrc.zipのソースコードについては、これはJDKのソースコードの一部にすぎず、上記のクラスのコードは存在しません。検索と追加後、上記のコードはAndroidアプリケーションでうまく機能します。これには、このクラスに対応するコードが含まれています。さらに、このクラスは、ceFormatexception、Cestreamexaxted、CharacterdeCoder、CardalenCoderクラス、および例外定義にも依存しています。
2012年2月23日に追加された:最初は、この記事を書き、RSA暗号化と復号化をサードパーティのパッケージに頼らずに実装しましたが、後で問題に遭遇しました。暗号化メソッド暗号化と復号化メソッドDecryptの両方で暗号オブジェクトを作成する必要があるため、このオブジェクトはGetInstanceを介してのみインスタンスを取得できます。それには2つのタイプがあります。1つ目は、プロバイダーではなくアルゴリズムのみを指定することです。 2つ目は両方を指定することです。最初はコードが実行される可能性がありますが、各暗号化の結果が異なることがわかります。その後、Cipherオブジェクトが使用するパブリックキーと秘密鍵が、コードで指定されたパブリックキーと秘密鍵ではなく、内部でランダムに生成されることが発見されました。奇妙なことに、プロバイダーを指定していないこのコードは、Androidアプリケーションを介して実行でき、各暗号化の結果は同じです。 Android SDKの一部のシステム開発機能に加えて、JDKの機能も実装していると思います。それは独自のJDKで対応するプロバイダーを提供した可能性があり、これにより、暗号化の結果が毎回同じになります。インターネット上のサンプルコードのようなBouncycastleプロバイダーを追加すると、各暗号化の結果は同じです。
読んでくれてありがとう、私はそれがあなたを助けることができることを願っています。このサイトへのご支援ありがとうございます!