RSA解密很慢
RSA decryption is very slow
我在 php 中实现了 RSA,我的私钥长 640 位,我使用中国提醒定理来获得更快的结果,但我仍然需要超过三秒的时间来解密一次一个 50 位长(AES 密钥),我认为这非常非常慢,考虑到在大多数 https 站点上它只需要几毫秒。
$dec = bcmod( bcadd( bcmul(bcmul($q,$cp),bcpowmod(bcmod($keyrsa,$p),$dp,$p)), bcmul(bcmul($p,$cq),bcpowmod(bcmod($keyrsa,$p),$dp,$p)) ) , $n );
如果您有兴趣,这就是我实现它的方式。几乎所有的变量都是预先计算的。
在 python 中使用相同的算法非常快,但由于某些原因 php 仍然较慢。
有没有更好的实现方式?
大多数 HTTPS 网站如何在如此大的流量下运行得如此之快?
我认为问题是类型转换,每次调用 bc
函数时都需要将字符串转换为内部表示,然后将其转换回十进制字符串,然后传递给下一个函数
尝试改用 GMP 整数数学,手册页 here
<?php
$keyrsa = gmp_init("9832475748957245");
$p = gmp_init("8354079484936541914927899085066667840301483360503839666157604136172921017528434146469774903867827180301976075982694562560689572638988092925269813627463374625291252908846201647344151611753461104963119608859115640201075591792459197160119945258486367627500121879818096099203595248003716117545512480479865709921453");
$q = gmp_init("938412744368825581535702355433426163883459511114687878154024994897102350822189947166755477679382811899594449736937158715413660429942933801527664946168421987845759422078910224872347655774496994538836516350730448938820126252589141481797770481863822310785941175596494671215977389040699889153301120914503446716507973489992786954188813");
//$cq = "90158151585243433649068545530051893622966883012518795089220114585310968302320502026270948815940384941612296625138324093461024924511161402917200931834290201708637643850750136849813026570271943168694883902320057242885955055614162225328861522256625184296048689139146938390662090382632227663474386093495477914592794162872990148364116";
//$cp = "7551459988262214427840190779497680155475105762407164553046829825327340315927179742834418691277481624391481553210225801715295088793857458100116513396506530756291114733889990865992240204940649387943199598796499358274552099683283819575613245477264444414822005200002309824389674861969207905172310540069768226872734";
$dp = gmp_init("1965665761161539274100682137662745374188584320118550509684142149687746121771396269757594095027724042423994370819457544131926958267997198335357603206461970500068530096199106269963329791000814377638381084437438974164958962774696281684734104766702674735882381618780728493930257705412639086481297054230556637628577");
//$dq = "883211994700071135563013981584401095419726598696176826497905877550213977244414067921652214286477940611383011517117325849801092169358055342614272890511455988560714750191915505762209558375997171330669662447746304883595412943613309629927313394695362174857356400561406749379743424979482248614871643213650302792007504461169681839236529");
$qtcp = gmp_init("7086386291576524054360302742239998876673708944686465411626570038380444601875306630964988910095131487662281790536626963003506657704070876201964033331286024035984707744160238401059534677753482122942131531324658709164939274183600052634838272332743659199253932999987961039598035528397374750903876542815898982226118836076739179152436733287292195730452100700462917916533108208521409272086529455286245592495898895482186435700595327952372741822199742491182942283075691359064307215568687412510144120677674012937164826009435459181454662134489129797327892892707673596353503035243628926739960488503739316122718017371542430284689864394081681732757524742");
//$d = "9684180457578041703423518212984665367413021472235946617919642829863937153436059290504589391395592577209702599096169971796160405050131992497221547725184873244919981572828194571494694548428547986158684865534112722970807920768563560619443671077664354596805006314087514740257760893103656422610790000570529248962650590971772121591956305661910290201820155312347599369833629985907639681332639927293587022614471157370529051414542594064576484579816117675667970018652822901408587669420741843654459983059048798380989538136593189533517910165268761423288024908153885735118716648190934832866700250304833422760360615089471368245425769057619094702167123265";
$n = gmp_init("7839574656134605188485705220035205297429588810857671071649234671794615790876809901837048554939289229169759246887375691454034613612011612973941252920387754531601889844670443224543324158251681703080840129241900775738273078717408596691930590872394953721223100349499416694494377865845817104018258571890428439636432369199417038685736648639886105668941162211691589720601790029355870681555006383931825756229459276736474343941175285895314774582071354222952445036285378330268675333052497389891203339480294275218891997254728399246701139093936159885498019009817278067080240490608754607645219870614833288791258716931448852885321580818328787411561305289");
$ptcq = gmp_init("753188364558081134125402477795206420755879866171205660022664633414171189001503270872059644844157741507477456350748728450527955907940736771977219589101730495617182100510204823483789480498199580138708597917242066573333804533808544057092318539651294521969167349511455654896342337448442353114382029074529457410313533122677859533299915352593909938489061511228671804068681820834461409468476928645580163733560381254287908240579957942942032759871611731769502753209686971204368117483809977381059218802620262281727171245292940065246476959447030088170126117109604470726737455365125680905259382111093972668540699559906422600631716424247105678803780548");
$gmpPowm = gmp_powm(gmp_mod($keyrsa, $p), $dp, $p);
$gmpResult = gmp_mod(gmp_add(gmp_mul($qtcp, $gmpPowm), gmp_mul($ptcq, $gmpPowm)), $n);
$dec = gmp_strval($gmpResult);
echo $dec . "\n";
我在 php 中实现了 RSA,我的私钥长 640 位,我使用中国提醒定理来获得更快的结果,但我仍然需要超过三秒的时间来解密一次一个 50 位长(AES 密钥),我认为这非常非常慢,考虑到在大多数 https 站点上它只需要几毫秒。
$dec = bcmod( bcadd( bcmul(bcmul($q,$cp),bcpowmod(bcmod($keyrsa,$p),$dp,$p)), bcmul(bcmul($p,$cq),bcpowmod(bcmod($keyrsa,$p),$dp,$p)) ) , $n );
如果您有兴趣,这就是我实现它的方式。几乎所有的变量都是预先计算的。
在 python 中使用相同的算法非常快,但由于某些原因 php 仍然较慢。
有没有更好的实现方式?
大多数 HTTPS 网站如何在如此大的流量下运行得如此之快?
我认为问题是类型转换,每次调用 bc
函数时都需要将字符串转换为内部表示,然后将其转换回十进制字符串,然后传递给下一个函数
尝试改用 GMP 整数数学,手册页 here
<?php
$keyrsa = gmp_init("9832475748957245");
$p = gmp_init("8354079484936541914927899085066667840301483360503839666157604136172921017528434146469774903867827180301976075982694562560689572638988092925269813627463374625291252908846201647344151611753461104963119608859115640201075591792459197160119945258486367627500121879818096099203595248003716117545512480479865709921453");
$q = gmp_init("938412744368825581535702355433426163883459511114687878154024994897102350822189947166755477679382811899594449736937158715413660429942933801527664946168421987845759422078910224872347655774496994538836516350730448938820126252589141481797770481863822310785941175596494671215977389040699889153301120914503446716507973489992786954188813");
//$cq = "90158151585243433649068545530051893622966883012518795089220114585310968302320502026270948815940384941612296625138324093461024924511161402917200931834290201708637643850750136849813026570271943168694883902320057242885955055614162225328861522256625184296048689139146938390662090382632227663474386093495477914592794162872990148364116";
//$cp = "7551459988262214427840190779497680155475105762407164553046829825327340315927179742834418691277481624391481553210225801715295088793857458100116513396506530756291114733889990865992240204940649387943199598796499358274552099683283819575613245477264444414822005200002309824389674861969207905172310540069768226872734";
$dp = gmp_init("1965665761161539274100682137662745374188584320118550509684142149687746121771396269757594095027724042423994370819457544131926958267997198335357603206461970500068530096199106269963329791000814377638381084437438974164958962774696281684734104766702674735882381618780728493930257705412639086481297054230556637628577");
//$dq = "883211994700071135563013981584401095419726598696176826497905877550213977244414067921652214286477940611383011517117325849801092169358055342614272890511455988560714750191915505762209558375997171330669662447746304883595412943613309629927313394695362174857356400561406749379743424979482248614871643213650302792007504461169681839236529");
$qtcp = gmp_init("7086386291576524054360302742239998876673708944686465411626570038380444601875306630964988910095131487662281790536626963003506657704070876201964033331286024035984707744160238401059534677753482122942131531324658709164939274183600052634838272332743659199253932999987961039598035528397374750903876542815898982226118836076739179152436733287292195730452100700462917916533108208521409272086529455286245592495898895482186435700595327952372741822199742491182942283075691359064307215568687412510144120677674012937164826009435459181454662134489129797327892892707673596353503035243628926739960488503739316122718017371542430284689864394081681732757524742");
//$d = "9684180457578041703423518212984665367413021472235946617919642829863937153436059290504589391395592577209702599096169971796160405050131992497221547725184873244919981572828194571494694548428547986158684865534112722970807920768563560619443671077664354596805006314087514740257760893103656422610790000570529248962650590971772121591956305661910290201820155312347599369833629985907639681332639927293587022614471157370529051414542594064576484579816117675667970018652822901408587669420741843654459983059048798380989538136593189533517910165268761423288024908153885735118716648190934832866700250304833422760360615089471368245425769057619094702167123265";
$n = gmp_init("7839574656134605188485705220035205297429588810857671071649234671794615790876809901837048554939289229169759246887375691454034613612011612973941252920387754531601889844670443224543324158251681703080840129241900775738273078717408596691930590872394953721223100349499416694494377865845817104018258571890428439636432369199417038685736648639886105668941162211691589720601790029355870681555006383931825756229459276736474343941175285895314774582071354222952445036285378330268675333052497389891203339480294275218891997254728399246701139093936159885498019009817278067080240490608754607645219870614833288791258716931448852885321580818328787411561305289");
$ptcq = gmp_init("753188364558081134125402477795206420755879866171205660022664633414171189001503270872059644844157741507477456350748728450527955907940736771977219589101730495617182100510204823483789480498199580138708597917242066573333804533808544057092318539651294521969167349511455654896342337448442353114382029074529457410313533122677859533299915352593909938489061511228671804068681820834461409468476928645580163733560381254287908240579957942942032759871611731769502753209686971204368117483809977381059218802620262281727171245292940065246476959447030088170126117109604470726737455365125680905259382111093972668540699559906422600631716424247105678803780548");
$gmpPowm = gmp_powm(gmp_mod($keyrsa, $p), $dp, $p);
$gmpResult = gmp_mod(gmp_add(gmp_mul($qtcp, $gmpPowm), gmp_mul($ptcq, $gmpPowm)), $n);
$dec = gmp_strval($gmpResult);
echo $dec . "\n";