OMG,到底在尋找什么..................
          (構(gòu)造一個(gè)完美的J2EE系統(tǒng)所需要的完整知識(shí)體系)
          posts - 198,  comments - 37,  trackbacks - 0

          原貼地址: http://www.aygfsteel.com/security/archive/2006/01/11/27547.aspx

          RSA協(xié)議我不再描述,大家可以看http://www.di-mgt.com.au/rsa_alg.html。
          RSA的密鑰對(duì)生成時(shí)間依賴于兩個(gè)因素,
          第一,密鑰的長度
          第二,素?cái)?shù)的篩選質(zhì)量

          在整個(gè)密鑰對(duì)生成過程中,RSA會(huì)隨機(jī)選擇兩個(gè)大素?cái)?shù),事實(shí)上,計(jì)算機(jī)的聰明
          程度還不足以判斷某個(gè)隨機(jī)選擇的大素?cái)?shù)是否真的不可分解,因此,你只能夠通過
          計(jì)算機(jī)程序來盡量將這個(gè)大隨機(jī)數(shù)不是素?cái)?shù)的幾率降到某個(gè)界限值(如0.0001)以下。

          RSA KeyPair分為公鑰和私鑰,你應(yīng)該這樣使用KeyPair:
          1,你使用私鑰來簽名,別人用你的公鑰來驗(yàn)證簽名
          2,別人用你的公鑰加密信息M->M',你用私鑰來解密信息M'->M

          雖然RSA經(jīng)受過多年深入的密碼分析,但大家在使用RSA的時(shí)候還是要注意以下事項(xiàng),
          否則RSA的安全性會(huì)大打折扣:

          1,合理的密鑰長度(setKeyLength)
          RSA1024至今是安全的,按照目前密碼分析和計(jì)算機(jī)硬件條件的發(fā)展,估計(jì)在未來5-10年,
          仍以難以破解。

          2,素?cái)?shù)確定性選擇(setCertaintyOfPrime)
          實(shí)際應(yīng)用中,選擇100就行了。

          3,選擇合理的padding(setRSAMode)
          RSA有三種模式,RAW, PKCS和OAEP,日常應(yīng)用中,我本人只使用PKCS(PKCS#1 v1.5)
          和OAEP(PKCS#1 v2.0)這兩種padding模式。
          padding跟安全性其實(shí)是緊密掛鉤的,有興趣的朋友可以看看PKCS#1標(biāo)準(zhǔn)討論。


          我編寫了一個(gè)RSAUtils的工具類,下面的該類的測試代碼的一部分。

          程序如下:
          ??RSAUtils utils =new RSAUtils();
          ??utils.setKeyLength(1024);
          ??utils.setCertaintyOfPrime(100);
          ??utils.setRSAMode(PKCS_RSA_MODE);?? //RAW =1? PKCS=2? OAEP=3
          ??utils.initRSAKeyPair();
          ??
          ??//查看公鑰
          ??RSAKeyParameters mypubkey=utils.getPublicKey();
          ??BigInteger mypubkey_modulus=mypubkey.getModulus();??
          ??BigInteger mypubkey_exponent=mypubkey.getExponent();
          ??System.out.println("##mypubkey的modulus長度="+mypubkey_modulus.bitLength());
          ??System.out.println("##mypubkey_modulus值="+mypubkey_modulus.toString());
          ??System.out.println("##mypubkey的exponent長度="+mypubkey.getExponent().bitLength());
          ??System.out.println("##mypubkey_exponent值="+mypubkey_exponent.toString());

          ??//查看私鑰
          ??RSAKeyParameters myprivkey=utils.getPrivateKey();
          ??BigInteger myprivkey_modulus=myprivkey.getModulus();
          ??System.out.println("##myprivkey的modulus長度="+myprivkey_modulus.bitLength());
          ??System.out.println("##myprivkey的modulus值="+myprivkey_modulus.toString());
          ??System.out.println("##myprivkey.getExponent()長度="+myprivkey.getExponent().bitLength());
          ??System.out.println("##myprivkey.getExponent()值="+myprivkey.getExponent());

          以下是輸出:
          ##mypubkey的modulus長度=1024
          ##mypubkey_modulus值=93806062666699782638132820491933031482836826566660997927543724649365705443512121003172409185855121369631538039111403612211728268332662414248776212969019881724066055080327735965218365399595323200109436472147258110417469825748181131149217613806780318374365617984326523029965066348377550281908277056378455106547
          ##mypubkey的exponent長度=2
          ##mypubkey_exponent值=3

          ##myprivkey的modulus長度=1024
          ##myprivkey的modulus值=93806062666699782638132820491933031482836826566660997927543724649365705443512121003172409185855121369631538039111403612211728268332662414248776212969019881724066055080327735965218365399595323200109436472147258110417469825748181131149217613806780318374365617984326523029965066348377550281908277056378455106547
          ##myprivkey.getExponent()長度=1023
          ##myprivkey.getExponent()值=62537375111133188425421880327955354321891217711107331951695816432910470295674747335448272790570080913087692026074269074807818845555108276165850808646013241363962278455328383552959397735977285649455021534046301135296075808377308404258909132811288204167107604525033796313576612747649866739561523887875979483707

          其中,要記住,公鑰的exponent即RSA算法中的e, e通常是3,17和65537
          X.509建議使用65537,PEM建議使用3,PKCS#1建議使用3或65537,一般來說,都是選擇3。

          私鑰的Exponent就是私鑰中最重要的部分,它就是私鑰區(qū)別于公鑰的地方!

          接著,我們看看RSA的加密,解密過程。

          通常,不要隨便對(duì)某一個(gè)別人發(fā)過來的東西進(jìn)行簽名(有潛在危險(xiǎn)),即使有這樣的必要,請(qǐng)先將它的文件進(jìn)行Digest或者HMAC
          處理后,再做簽名。
          為了說明RSA是如何加密信息的,我先讓大家脫離MD5/SHA1等輔助算法(沒有人會(huì)單獨(dú)使用RSA,RSAwithMD5,RSAwithSHA1才是常用的使用方法),來單獨(dú)看看RSA本身:

          大家習(xí)慣了DES/IDEA,再看RSA的加密,可能會(huì)有一些不習(xí)慣,因?yàn)镽SA雖然也可以看成是基于Block的加密,但是,RSA的輸入和輸出的Block的大小是不一樣的,Block的大小依賴于你所使用的RSA Key的長度和RSA的padding模式。
          在RSAUtils測試用例中,分別對(duì)RSA設(shè)置三種長度的Key(768,1024,2048)和2種padding模式(PKCS 1.5和OAEP),結(jié)果如下:

          RSA??????????????? InBlock大小?? OutBlock大小? (單位,字節(jié))
          768bit/PKCS??????? 85??????????????? 96
          1024bit/PKCS???? 117?????????????? 128
          2048bit/PKCS???? 245?????????????? 256
          768bit/OAEP??????? 54??????????????? 96
          1024bit/OAEP???? 86?????????????? 128
          2048bit/OAEP???? 214?????????????? 256

          大家可以看到,相同密鑰長度, 加密出來的密文長度要比明文要長,且OAEP的InBlock/OutBlock要比PKCS的InBlock/OutBlock要小,單從熵的角度,意味著OAEP padding模式引入更多的熵,OAEP要比PKCS更安全(事實(shí)上,為何提出OAEP代替PKCS,大家可以到RSA網(wǎng)站看看OAEP文檔 http://www.rsasecurity.com/rsalabs/node.asp?id=2125)。


          下面,RSAUtils是我寫的針對(duì)BouncyCastle的一個(gè)工具類,它封裝了BouncyCastle的crypto中的RSAEngine,基本上,我很少單獨(dú)使用RSAUtils,我更多的是結(jié)合DiegestUtils來使用。

          posted on 2007-01-22 15:34 OMG 閱讀(468) 評(píng)論(0)  編輯  收藏 所屬分類: Webservice

          <2007年1月>
          31123456
          78910111213
          14151617181920
          21222324252627
          28293031123
          45678910

          常用鏈接

          留言簿(1)

          隨筆分類

          隨筆檔案

          IT風(fēng)云人物

          文檔

          朋友

          相冊(cè)

          經(jīng)典網(wǎng)站

          搜索

          •  

          最新評(píng)論

          閱讀排行榜

          評(píng)論排行榜

          主站蜘蛛池模板: 清水河县| 安图县| 石狮市| 牡丹江市| 宝丰县| 荥经县| 长岛县| 闻喜县| 分宜县| 永和县| 蓝山县| 南宫市| 安义县| 济源市| 安仁县| 荔浦县| 福泉市| 遵化市| 承德市| 鲜城| 南通市| 安丘市| 漯河市| 当雄县| 名山县| 桑植县| 阜阳市| 辽源市| 杂多县| 都匀市| 大庆市| 永仁县| 利川市| 吉安县| 贵州省| 襄汾县| 乐平市| 普格县| 尚义县| 务川| 抚远县|