Advertisement
1lann

rsa-crypt

Aug 24th, 2015
1,102
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Lua 25.84 KB | None | 0 0
  1. --
  2. -- RSA Encryption/Decryption Library
  3. -- By 1lann
  4. --
  5. -- Refer to license: http://pastebin.com/9gWSyqQt
  6. --
  7.  
  8. --
  9. -- Start of third-party libraries/helpers
  10. --
  11.  
  12. -- two functions to help make Lua act more like C
  13. local function fl(x)
  14.     if x < 0 then
  15.         return math.ceil(x) + 0 -- make -0 go away
  16.     else
  17.         return math.floor(x)
  18.     end
  19. end
  20.  
  21. local function cmod(a, b)
  22.     local x = a % b
  23.     if a < 0 and x > 0 then
  24.         x = x - b
  25.     end
  26.     return x
  27. end
  28.  
  29.  
  30. local radix = 2^24 -- maybe up to 2^26 is safe?
  31. local radix_sqrt = fl(math.sqrt(radix))
  32.  
  33. local bigintmt -- forward decl
  34.  
  35. local function alloc()
  36.     local bi = {}
  37.     setmetatable(bi, bigintmt)
  38.     bi.comps = {}
  39.     bi.sign = 1;
  40.     return bi
  41. end
  42.  
  43. local function clone(a)
  44.     local bi = alloc()
  45.     bi.sign = a.sign
  46.     local c = bi.comps
  47.     local ac = a.comps
  48.     for i = 1, #ac do
  49.         c[i] = ac[i]
  50.     end
  51.     return bi
  52. end
  53.  
  54. local function normalize(bi, notrunc)
  55.     local c = bi.comps
  56.     local v
  57.     -- borrow for negative components
  58.     for i = 1, #c - 1 do
  59.         v = c[i]
  60.         if v < 0 then
  61.             c[i+1] = c[i+1] + fl(v / radix) - 1
  62.             v = cmod(v, radix)
  63.             if v ~= 0 then
  64.                 c[i] = v + radix
  65.             else
  66.                 c[i] = v
  67.                 c[i+1] = c[i+1] + 1
  68.             end
  69.         end
  70.     end
  71.     -- is top component negative?
  72.     if c[#c] < 0 then
  73.         -- switch the sign and fix components
  74.         bi.sign = -bi.sign
  75.         for i = 1, #c - 1 do
  76.             v = c[i]
  77.             c[i] = radix - v
  78.             c[i+1] = c[i+1] + 1
  79.         end
  80.         c[#c] = -c[#c]
  81.     end
  82.     -- carry for components larger than radix
  83.     for i = 1, #c do
  84.         v = c[i]
  85.         if v > radix then
  86.             c[i+1] = (c[i+1] or 0) + fl(v / radix)
  87.             c[i] = cmod(v, radix)
  88.         end
  89.     end
  90.     -- trim off leading zeros
  91.     if not notrunc then
  92.         for i = #c, 2, -1 do
  93.             if c[i] == 0 then
  94.                 c[i] = nil
  95.             else
  96.                 break
  97.             end
  98.         end
  99.     end
  100.     -- check for -0
  101.     if #c == 1 and c[1] == 0 and bi.sign == -1 then
  102.         bi.sign = 1
  103.     end
  104. end
  105.  
  106. local function negate(a)
  107.     local bi = clone(a)
  108.     bi.sign = -bi.sign
  109.     return bi
  110. end
  111.  
  112. local function compare(a, b)
  113.     local ac, bc = a.comps, b.comps
  114.     local as, bs = a.sign, b.sign
  115.     if ac == bc then
  116.         return 0
  117.     elseif as > bs then
  118.         return 1
  119.     elseif as < bs then
  120.         return -1
  121.     elseif #ac > #bc then
  122.         return as
  123.     elseif #ac < #bc then
  124.         return -as
  125.     end
  126.     for i = #ac, 1, -1 do
  127.         if ac[i] > bc[i] then
  128.             return as
  129.         elseif ac[i] < bc[i] then
  130.             return -as
  131.         end
  132.     end
  133.     return 0
  134. end
  135.  
  136. local function lt(a, b)
  137.     return compare(a, b) < 0
  138. end
  139.  
  140. local function eq(a, b)
  141.     return compare(a, b) == 0
  142. end
  143.  
  144. local function le(a, b)
  145.     return compare(a, b) <= 0
  146. end
  147.  
  148. local function addint(a, n)
  149.     local bi = clone(a)
  150.     if bi.sign == 1 then
  151.         bi.comps[1] = bi.comps[1] + n
  152.     else
  153.         bi.comps[1] = bi.comps[1] - n
  154.     end
  155.     normalize(bi)
  156.     return bi
  157. end
  158.  
  159. local function add(a, b)
  160.     if type(a) == "number" then
  161.         return addint(b, a)
  162.     elseif type(b) == "number" then
  163.         return addint(a, b)
  164.     end
  165.     local bi = clone(a)
  166.     local sign = bi.sign == b.sign
  167.     local c = bi.comps
  168.     for i = #c + 1, #b.comps do
  169.         c[i] = 0
  170.     end
  171.     local bc = b.comps
  172.     for i = 1, #bc do
  173.         local v = bc[i]
  174.         if sign then
  175.             c[i] = c[i] + v
  176.         else
  177.             c[i] = c[i] - v
  178.         end
  179.     end
  180.     normalize(bi)
  181.     return bi
  182. end
  183.  
  184. local function sub(a, b)
  185.     if type(b) == "number" then
  186.         return addint(a, -b)
  187.     elseif type(a) == "number" then
  188.         a = bigint(a)
  189.     end
  190.     return add(a, negate(b))
  191. end
  192.  
  193. local function mulint(a, b)
  194.     local bi = clone(a)
  195.     if b < 0 then
  196.         b = -b
  197.         bi.sign = -bi.sign
  198.     end
  199.     local bc = bi.comps
  200.     for i = 1, #bc do
  201.         bc[i] = bc[i] * b
  202.     end
  203.     normalize(bi)
  204.     return bi
  205. end
  206.  
  207. local function multiply(a, b)
  208.     local bi = alloc()
  209.     local c = bi.comps
  210.     local ac, bc = a.comps, b.comps
  211.     for i = 1, #ac + #bc do
  212.         c[i] = 0
  213.     end
  214.     for i = 1, #ac do
  215.         for j = 1, #bc do
  216.             c[i+j-1] = c[i+j-1] + ac[i] * bc[j]
  217.         end
  218.         -- keep the zeroes
  219.         normalize(bi, true)
  220.     end
  221.     normalize(bi)
  222.     if bi ~= bigint(0) then
  223.         bi.sign = a.sign * b.sign
  224.     end
  225.     return bi
  226. end
  227.  
  228. local function kmul(a, b)
  229.     local ac, bc = a.comps, b.comps
  230.     local an, bn = #a.comps, #b.comps
  231.     local bi, bj, bk, bl = alloc(), alloc(), alloc(), alloc()
  232.     local ic, jc, kc, lc = bi.comps, bj.comps, bk.comps, bl.comps
  233.  
  234.     local n = fl((math.max(an, bn) + 1) / 2)
  235.     for i = 1, n do
  236.         ic[i] = (i + n <= an) and ac[i+n] or 0
  237.         jc[i] = (i <= an) and ac[i] or 0
  238.         kc[i] = (i + n <= bn) and bc[i+n] or 0
  239.         lc[i] = (i <= bn) and bc[i] or 0
  240.     end
  241.     normalize(bi)
  242.     normalize(bj)
  243.     normalize(bk)
  244.     normalize(bl)
  245.     local ik = bi * bk
  246.     local jl = bj * bl
  247.     local mid = (bi + bj) * (bk + bl) - ik - jl
  248.     local mc = mid.comps
  249.     local ikc = ik.comps
  250.     local jlc = jl.comps
  251.     for i = 1, #ikc + n*2 do -- fill it up
  252.         jlc[i] = jlc[i] or 0
  253.     end
  254.     for i = 1, #mc do
  255.         jlc[i+n] = jlc[i+n] + mc[i]
  256.     end
  257.     for i = 1, #ikc do
  258.         jlc[i+n*2] = jlc[i+n*2] + ikc[i]
  259.     end
  260.     jl.sign = a.sign * b.sign
  261.     normalize(jl)
  262.     return jl
  263. end
  264.  
  265. local kthresh = 12
  266.  
  267. local function mul(a, b)
  268.     if type(a) == "number" then
  269.         return mulint(b, a)
  270.     elseif type(b) == "number" then
  271.         return mulint(a, b)
  272.     end
  273.     if #a.comps < kthresh or #b.comps < kthresh then
  274.         return multiply(a, b)
  275.     end
  276.     return kmul(a, b)
  277. end
  278.  
  279. local function divint(numer, denom)
  280.     local bi = clone(numer)
  281.     if denom < 0 then
  282.         denom = -denom
  283.         bi.sign = -bi.sign
  284.     end
  285.     local r = 0
  286.     local c = bi.comps
  287.     for i = #c, 1, -1 do
  288.         r = r * radix + c[i]
  289.         c[i] = fl(r / denom)
  290.         r = cmod(r, denom)
  291.     end
  292.     normalize(bi)
  293.     return bi
  294. end
  295.  
  296. local function multi_divide(numer, denom)
  297.     local n = #denom.comps
  298.     local approx = divint(numer, denom.comps[n])
  299.     for i = n, #approx.comps do
  300.         approx.comps[i - n + 1] = approx.comps[i]
  301.     end
  302.     for i = #approx.comps, #approx.comps - n + 2, -1 do
  303.         approx.comps[i] = nil
  304.     end
  305.     local rem = approx * denom - numer
  306.     if rem < denom then
  307.         quotient = approx
  308.     else
  309.         quotient = approx - multi_divide(rem, denom)
  310.     end
  311.     return quotient
  312. end
  313.  
  314. local function multi_divide_wrap(numer, denom)
  315.     -- we use a successive approximation method, but it doesn't work
  316.     -- if the high order component is too small.  adjust if needed.
  317.     if denom.comps[#denom.comps] < radix_sqrt then
  318.         numer = mulint(numer, radix_sqrt)
  319.         denom = mulint(denom, radix_sqrt)
  320.     end
  321.     return multi_divide(numer, denom)
  322. end
  323.  
  324. local function div(numer, denom)
  325.     if type(denom) == "number" then
  326.         if denom == 0 then
  327.             error("divide by 0", 2)
  328.         end
  329.         return divint(numer, denom)
  330.     elseif type(numer) == "number" then
  331.         numer = bigint(numer)
  332.     end
  333.     -- check signs and trivial cases
  334.     local sign = 1
  335.     local cmp = compare(denom, bigint(0))
  336.     if cmp == 0 then
  337.         error("divide by 0", 2)
  338.     elseif cmp == -1 then
  339.         sign = -sign
  340.         denom = negate(denom)
  341.     end
  342.     cmp = compare(numer, bigint(0))
  343.     if cmp == 0 then
  344.         return bigint(0)
  345.     elseif cmp == -1 then
  346.         sign = -sign
  347.         numer = negate(numer)
  348.     end
  349.     cmp = compare(numer, denom)
  350.     if cmp == -1 then
  351.         return bigint(0)
  352.     elseif cmp == 0 then
  353.         return bigint(sign)
  354.     end
  355.     local bi
  356.     -- if small enough, do it the easy way
  357.     if #denom.comps == 1 then
  358.         bi = divint(numer, denom.comps[1])
  359.     else
  360.         bi = multi_divide_wrap(numer, denom)
  361.     end
  362.     if sign == -1 then
  363.         bi = negate(bi)
  364.     end
  365.     return bi
  366. end
  367.  
  368. local function intrem(bi, m)
  369.     if m < 0 then
  370.         m = -m
  371.     end
  372.     local rad_r = 1
  373.     local r = 0
  374.     local bc = bi.comps
  375.     for i = 1, #bc do
  376.         local v = bc[i]
  377.         r = cmod(r + v * rad_r, m)
  378.         rad_r = cmod(rad_r * radix, m)
  379.     end
  380.     if bi.sign < 1 then
  381.         r = -r
  382.     end
  383.     return r
  384. end
  385.  
  386. local function intmod(bi, m)
  387.     local r = intrem(bi, m)
  388.     if r < 0 then
  389.         r = r + m
  390.     end
  391.     return r
  392. end
  393.  
  394. local function rem(bi, m)
  395.     if type(m) == "number" then
  396.         return bigint(intrem(bi, m))
  397.     elseif type(bi) == "number" then
  398.         bi = bigint(bi)
  399.     end
  400.  
  401.     return bi - ((bi / m) * m)
  402. end
  403.  
  404. local function mod(a, m)
  405.     local bi = rem(a, m)
  406.     if bi.sign == -1 then
  407.         bi = bi + m
  408.     end
  409.     return bi
  410. end
  411.  
  412. local printscale = 10000000
  413. local printscalefmt = string.format("%%.%dd", math.log10(printscale))
  414. local function makestr(bi, s)
  415.     if bi >= bigint(printscale) then
  416.         makestr(divint(bi, printscale), s)
  417.     end
  418.     table.insert(s, string.format(printscalefmt, intmod(bi, printscale)))
  419. end
  420.  
  421. local function biginttostring(bi)
  422.     local s = {}
  423.     if bi < bigint(0) then
  424.         bi = negate(bi)
  425.         table.insert(s, "-")
  426.     end
  427.     makestr(bi, s)
  428.     s = table.concat(s):gsub("^0*", "")
  429.     if s == "" then s = "0" end
  430.     return s
  431. end
  432.  
  433. local function biginttonumber(bi)
  434.     return tonumber(biginttostring(bi))
  435. end
  436.  
  437. bigintmt = {
  438.     __add = add,
  439.     __sub = sub,
  440.     __mul = mul,
  441.     __div = div,
  442.     __mod = mod,
  443.     __unm = negate,
  444.     __eq = eq,
  445.     __lt = lt,
  446.     __le = le,
  447.     __tostring = biginttostring,
  448. }
  449.  
  450. local cache = {}
  451. local ncache = 0
  452.  
  453. function bigint(n)
  454.     if cache[n] then
  455.         return cache[n]
  456.     end
  457.     local bi
  458.     if type(n) == "string" then
  459.         local digits = { n:byte(1, -1) }
  460.         for i = 1, #digits do
  461.             digits[i] = string.char(digits[i])
  462.         end
  463.         local start = 1
  464.         local sign = 1
  465.         if digits[i] == '-' then
  466.             sign = -1
  467.             start = 2
  468.         end
  469.         bi = bigint(0)
  470.         for i = start, #digits do
  471.             bi = addint(mulint(bi, 10), tonumber(digits[i]))
  472.         end
  473.         bi = mulint(bi, sign)
  474.     else
  475.         bi = alloc()
  476.         bi.comps[1] = n
  477.         normalize(bi)
  478.     end
  479.     if ncache > 100 then
  480.         cache = {}
  481.         ncache = 0
  482.     end
  483.     cache[n] = bi
  484.     ncache = ncache + 1
  485.     return bi
  486. end
  487.  
  488. --
  489. -- Start of my code
  490. --
  491.  
  492. local powersTwo = {
  493. bigint("2"),
  494. bigint("4"),
  495. bigint("8"),
  496. bigint("16"),
  497. bigint("32"),
  498. bigint("64"),
  499. bigint("128"),
  500. bigint("256"),
  501. bigint("512"),
  502. bigint("1024"),
  503. bigint("2048"),
  504. bigint("4096"),
  505. bigint("8192"),
  506. bigint("16384"),
  507. bigint("32768"),
  508. bigint("65536"),
  509. bigint("131072"),
  510. bigint("262144"),
  511. bigint("524288"),
  512. bigint("1048576"),
  513. bigint("2097152"),
  514. bigint("4194304"),
  515. bigint("8388608"),
  516. bigint("16777216"),
  517. bigint("33554432"),
  518. bigint("67108864"),
  519. bigint("134217728"),
  520. bigint("268435456"),
  521. bigint("536870912"),
  522. bigint("1073741824"),
  523. bigint("2147483648"),
  524. bigint("4294967296"),
  525. bigint("8589934592"),
  526. bigint("17179869184"),
  527. bigint("34359738368"),
  528. bigint("68719476736"),
  529. bigint("137438953472"),
  530. bigint("274877906944"),
  531. bigint("549755813888"),
  532. bigint("1099511627776"),
  533. bigint("2199023255552"),
  534. bigint("4398046511104"),
  535. bigint("8796093022208"),
  536. bigint("17592186044416"),
  537. bigint("35184372088832"),
  538. bigint("70368744177664"),
  539. bigint("140737488355328"),
  540. bigint("281474976710656"),
  541. bigint("562949953421312"),
  542. bigint("1125899906842624"),
  543. bigint("2251799813685248"),
  544. bigint("4503599627370496"),
  545. bigint("9007199254740992"),
  546. bigint("18014398509481984"),
  547. bigint("36028797018963968"),
  548. bigint("72057594037927936"),
  549. bigint("144115188075855872"),
  550. bigint("288230376151711744"),
  551. bigint("576460752303423488"),
  552. bigint("1152921504606846976"),
  553. bigint("2305843009213693952"),
  554. bigint("4611686018427387904"),
  555. bigint("9223372036854775808"),
  556. bigint("18446744073709551616"),
  557. bigint("36893488147419103232"),
  558. bigint("73786976294838206464"),
  559. bigint("147573952589676412928"),
  560. bigint("295147905179352825856"),
  561. bigint("590295810358705651712"),
  562. bigint("1180591620717411303424"),
  563. bigint("2361183241434822606848"),
  564. bigint("4722366482869645213696"),
  565. bigint("9444732965739290427392"),
  566. bigint("18889465931478580854784"),
  567. bigint("37778931862957161709568"),
  568. bigint("75557863725914323419136"),
  569. bigint("151115727451828646838272"),
  570. bigint("302231454903657293676544"),
  571. bigint("604462909807314587353088"),
  572. bigint("1208925819614629174706176"),
  573. bigint("2417851639229258349412352"),
  574. bigint("4835703278458516698824704"),
  575. bigint("9671406556917033397649408"),
  576. bigint("19342813113834066795298816"),
  577. bigint("38685626227668133590597632"),
  578. bigint("77371252455336267181195264"),
  579. bigint("154742504910672534362390528"),
  580. bigint("309485009821345068724781056"),
  581. bigint("618970019642690137449562112"),
  582. bigint("1237940039285380274899124224"),
  583. bigint("2475880078570760549798248448"),
  584. bigint("4951760157141521099596496896"),
  585. bigint("9903520314283042199192993792"),
  586. bigint("19807040628566084398385987584"),
  587. bigint("39614081257132168796771975168"),
  588. bigint("79228162514264337593543950336"),
  589. bigint("158456325028528675187087900672"),
  590. bigint("316912650057057350374175801344"),
  591. bigint("633825300114114700748351602688"),
  592. bigint("1267650600228229401496703205376"),
  593. bigint("2535301200456458802993406410752"),
  594. bigint("5070602400912917605986812821504"),
  595. bigint("10141204801825835211973625643008"),
  596. bigint("20282409603651670423947251286016"),
  597. bigint("40564819207303340847894502572032"),
  598. bigint("81129638414606681695789005144064"),
  599. bigint("162259276829213363391578010288128"),
  600. bigint("324518553658426726783156020576256"),
  601. bigint("649037107316853453566312041152512"),
  602. bigint("1298074214633706907132624082305024"),
  603. bigint("2596148429267413814265248164610048"),
  604. bigint("5192296858534827628530496329220096"),
  605. bigint("10384593717069655257060992658440192"),
  606. bigint("20769187434139310514121985316880384"),
  607. bigint("41538374868278621028243970633760768"),
  608. bigint("83076749736557242056487941267521536"),
  609. bigint("166153499473114484112975882535043072"),
  610. bigint("332306998946228968225951765070086144"),
  611. bigint("664613997892457936451903530140172288"),
  612. bigint("1329227995784915872903807060280344576"),
  613. bigint("2658455991569831745807614120560689152"),
  614. bigint("5316911983139663491615228241121378304"),
  615. bigint("10633823966279326983230456482242756608"),
  616. bigint("21267647932558653966460912964485513216"),
  617. bigint("42535295865117307932921825928971026432"),
  618. bigint("85070591730234615865843651857942052864"),
  619. bigint("170141183460469231731687303715884105728"),
  620. bigint("340282366920938463463374607431768211456"),
  621. bigint("680564733841876926926749214863536422912"),
  622. bigint("1361129467683753853853498429727072845824"),
  623. bigint("2722258935367507707706996859454145691648"),
  624. bigint("5444517870735015415413993718908291383296"),
  625. bigint("10889035741470030830827987437816582766592"),
  626. bigint("21778071482940061661655974875633165533184"),
  627. bigint("43556142965880123323311949751266331066368"),
  628. bigint("87112285931760246646623899502532662132736"),
  629. bigint("174224571863520493293247799005065324265472"),
  630. bigint("348449143727040986586495598010130648530944"),
  631. bigint("696898287454081973172991196020261297061888"),
  632. bigint("1393796574908163946345982392040522594123776"),
  633. bigint("2787593149816327892691964784081045188247552"),
  634. bigint("5575186299632655785383929568162090376495104"),
  635. bigint("11150372599265311570767859136324180752990208"),
  636. bigint("22300745198530623141535718272648361505980416"),
  637. bigint("44601490397061246283071436545296723011960832"),
  638. bigint("89202980794122492566142873090593446023921664"),
  639. bigint("178405961588244985132285746181186892047843328"),
  640. bigint("356811923176489970264571492362373784095686656"),
  641. bigint("713623846352979940529142984724747568191373312"),
  642. bigint("1427247692705959881058285969449495136382746624"),
  643. bigint("2854495385411919762116571938898990272765493248"),
  644. bigint("5708990770823839524233143877797980545530986496"),
  645. bigint("11417981541647679048466287755595961091061972992"),
  646. bigint("22835963083295358096932575511191922182123945984"),
  647. bigint("45671926166590716193865151022383844364247891968"),
  648. bigint("91343852333181432387730302044767688728495783936"),
  649. bigint("182687704666362864775460604089535377456991567872"),
  650. bigint("365375409332725729550921208179070754913983135744"),
  651. bigint("730750818665451459101842416358141509827966271488"),
  652. bigint("1461501637330902918203684832716283019655932542976"),
  653. bigint("2923003274661805836407369665432566039311865085952"),
  654. bigint("5846006549323611672814739330865132078623730171904"),
  655. bigint("11692013098647223345629478661730264157247460343808"),
  656. bigint("23384026197294446691258957323460528314494920687616"),
  657. bigint("46768052394588893382517914646921056628989841375232"),
  658. bigint("93536104789177786765035829293842113257979682750464"),
  659. bigint("187072209578355573530071658587684226515959365500928"),
  660. bigint("374144419156711147060143317175368453031918731001856"),
  661. bigint("748288838313422294120286634350736906063837462003712"),
  662. bigint("1496577676626844588240573268701473812127674924007424"),
  663. bigint("2993155353253689176481146537402947624255349848014848"),
  664. bigint("5986310706507378352962293074805895248510699696029696"),
  665. bigint("11972621413014756705924586149611790497021399392059392"),
  666. bigint("23945242826029513411849172299223580994042798784118784"),
  667. bigint("47890485652059026823698344598447161988085597568237568"),
  668. bigint("95780971304118053647396689196894323976171195136475136"),
  669. bigint("191561942608236107294793378393788647952342390272950272"),
  670. bigint("383123885216472214589586756787577295904684780545900544"),
  671. bigint("766247770432944429179173513575154591809369561091801088"),
  672. bigint("1532495540865888858358347027150309183618739122183602176"),
  673. bigint("3064991081731777716716694054300618367237478244367204352"),
  674. bigint("6129982163463555433433388108601236734474956488734408704"),
  675. bigint("12259964326927110866866776217202473468949912977468817408"),
  676. bigint("24519928653854221733733552434404946937899825954937634816"),
  677. bigint("49039857307708443467467104868809893875799651909875269632"),
  678. bigint("98079714615416886934934209737619787751599303819750539264"),
  679. bigint("196159429230833773869868419475239575503198607639501078528"),
  680. bigint("392318858461667547739736838950479151006397215279002157056"),
  681. bigint("784637716923335095479473677900958302012794430558004314112"),
  682. bigint("1569275433846670190958947355801916604025588861116008628224"),
  683. bigint("3138550867693340381917894711603833208051177722232017256448"),
  684. bigint("6277101735386680763835789423207666416102355444464034512896"),
  685. bigint("12554203470773361527671578846415332832204710888928069025792"),
  686. bigint("25108406941546723055343157692830665664409421777856138051584"),
  687. bigint("50216813883093446110686315385661331328818843555712276103168"),
  688. bigint("100433627766186892221372630771322662657637687111424552206336"),
  689. bigint("200867255532373784442745261542645325315275374222849104412672"),
  690. bigint("401734511064747568885490523085290650630550748445698208825344"),
  691. bigint("803469022129495137770981046170581301261101496891396417650688"),
  692. bigint("1606938044258990275541962092341162602522202993782792835301376"),
  693. bigint("3213876088517980551083924184682325205044405987565585670602752"),
  694. bigint("6427752177035961102167848369364650410088811975131171341205504"),
  695. bigint("12855504354071922204335696738729300820177623950262342682411008"),
  696. bigint("25711008708143844408671393477458601640355247900524685364822016"),
  697. bigint("51422017416287688817342786954917203280710495801049370729644032"),
  698. bigint("102844034832575377634685573909834406561420991602098741459288064"),
  699. bigint("205688069665150755269371147819668813122841983204197482918576128"),
  700. bigint("411376139330301510538742295639337626245683966408394965837152256"),
  701. bigint("822752278660603021077484591278675252491367932816789931674304512"),
  702. bigint("1645504557321206042154969182557350504982735865633579863348609024"),
  703. bigint("3291009114642412084309938365114701009965471731267159726697218048"),
  704. bigint("6582018229284824168619876730229402019930943462534319453394436096"),
  705. bigint("13164036458569648337239753460458804039861886925068638906788872192"),
  706. bigint("26328072917139296674479506920917608079723773850137277813577744384"),
  707. bigint("52656145834278593348959013841835216159447547700274555627155488768"),
  708. bigint("105312291668557186697918027683670432318895095400549111254310977536"),
  709. bigint("210624583337114373395836055367340864637790190801098222508621955072"),
  710. bigint("421249166674228746791672110734681729275580381602196445017243910144"),
  711. bigint("842498333348457493583344221469363458551160763204392890034487820288"),
  712. bigint("1684996666696914987166688442938726917102321526408785780068975640576"),
  713. bigint("3369993333393829974333376885877453834204643052817571560137951281152"),
  714. bigint("6739986666787659948666753771754907668409286105635143120275902562304"),
  715. bigint("13479973333575319897333507543509815336818572211270286240551805124608"),
  716. bigint("26959946667150639794667015087019630673637144422540572481103610249216"),
  717. bigint("53919893334301279589334030174039261347274288845081144962207220498432"),
  718. bigint("107839786668602559178668060348078522694548577690162289924414440996864"),
  719. bigint("215679573337205118357336120696157045389097155380324579848828881993728"),
  720. bigint("431359146674410236714672241392314090778194310760649159697657763987456"),
  721. bigint("862718293348820473429344482784628181556388621521298319395315527974912"),
  722. bigint("1725436586697640946858688965569256363112777243042596638790631055949824"),
  723. bigint("3450873173395281893717377931138512726225554486085193277581262111899648"),
  724. bigint("6901746346790563787434755862277025452451108972170386555162524223799296"),
  725. bigint("13803492693581127574869511724554050904902217944340773110325048447598592"),
  726. bigint("27606985387162255149739023449108101809804435888681546220650096895197184"),
  727. bigint("55213970774324510299478046898216203619608871777363092441300193790394368"),
  728. bigint("110427941548649020598956093796432407239217743554726184882600387580788736"),
  729. bigint("220855883097298041197912187592864814478435487109452369765200775161577472"),
  730. bigint("441711766194596082395824375185729628956870974218904739530401550323154944"),
  731. bigint("883423532389192164791648750371459257913741948437809479060803100646309888"),
  732. bigint("1766847064778384329583297500742918515827483896875618958121606201292619776"),
  733. bigint("3533694129556768659166595001485837031654967793751237916243212402585239552"),
  734. bigint("7067388259113537318333190002971674063309935587502475832486424805170479104"),
  735. bigint("14134776518227074636666380005943348126619871175004951664972849610340958208"),
  736. bigint("28269553036454149273332760011886696253239742350009903329945699220681916416"),
  737. bigint("56539106072908298546665520023773392506479484700019806659891398441363832832"),
  738. bigint("113078212145816597093331040047546785012958969400039613319782796882727665664"),
  739. bigint("226156424291633194186662080095093570025917938800079226639565593765455331328"),
  740. bigint("452312848583266388373324160190187140051835877600158453279131187530910662656"),
  741. bigint("904625697166532776746648320380374280103671755200316906558262375061821325312"),
  742. bigint("1809251394333065553493296640760748560207343510400633813116524750123642650624"),
  743. bigint("3618502788666131106986593281521497120414687020801267626233049500247285301248"),
  744. bigint("7237005577332262213973186563042994240829374041602535252466099000494570602496"),
  745. bigint("14474011154664524427946373126085988481658748083205070504932198000989141204992"),
  746. bigint("28948022309329048855892746252171976963317496166410141009864396001978282409984"),
  747. bigint("57896044618658097711785492504343953926634992332820282019728792003956564819968"),
  748. bigint("115792089237316195423570985008687907853269984665640564039457584007913129639936"),
  749. }
  750.  
  751. powersTwo[0] = bigint("1")
  752.  
  753. local bigZero = bigint(0)
  754. local bigOne = bigint(1)
  755.  
  756. local function numberToBytes(num, bits, byteSize)
  757.     if bits > #powersTwo then
  758.         error("Too many bits. Must be <= " .. #powersTwo .. ".")
  759.     end
  760.  
  761.     num = bigint(num)
  762.  
  763.     local resultBits = {}
  764.     resultBits[1] = {}
  765.     for i = bits - 1, 0, -1 do
  766.         local expVal = powersTwo[i]
  767.         local resultant = num - expVal
  768.         if expVal <= resultant then
  769.             -- Invalid data!
  770.             return nil
  771.         end
  772.  
  773.         if resultant < bigZero then
  774.             -- A zero bit
  775.             if #(resultBits[#resultBits]) >= byteSize then
  776.                 table.insert(resultBits, {0})
  777.             else
  778.                 table.insert(resultBits[#resultBits], 0)
  779.             end
  780.         else
  781.             -- A one bit
  782.             num = resultant
  783.             if #(resultBits[#resultBits]) >= byteSize then
  784.                 table.insert(resultBits, {1})
  785.             else
  786.                 table.insert(resultBits[#resultBits], 1)
  787.             end
  788.         end
  789.  
  790.         if num == bigint(0) then
  791.             break
  792.         end
  793.     end
  794.  
  795.     local results = {}
  796.     for _, binarySeq in pairs(resultBits) do
  797.         local thisResult = 0
  798.         for k, bin in pairs(binarySeq) do
  799.             if bin == 1 then
  800.                 thisResult = thisResult + 2^(byteSize - k)
  801.             end
  802.         end
  803.         table.insert(results, thisResult)
  804.     end
  805.  
  806.     return results
  807. end
  808.  
  809. local function bytesToNumber(bytes, bits, byteSize)
  810.     if bits > #powersTwo then
  811.         error("Too many bits. Must be <= " .. #powersTwo .. ".")
  812.     end
  813.  
  814.     if #bytes > bits/byteSize then
  815.         error("Too many bytes to store into the number of bits available. Must be <= " ..
  816.             bits/byteSize .. ".")
  817.     end
  818.  
  819.     local binary = {}
  820.     for _, byte in pairs(bytes) do
  821.         for i = byteSize - 1, 0, -1 do
  822.             if byte - (2 ^ i) < 0 then
  823.                 table.insert(binary, 0)
  824.             else
  825.                 table.insert(binary, 1)
  826.                 byte = byte - (2 ^ i)
  827.             end
  828.         end
  829.     end
  830.  
  831.     local num = bigint(0)
  832.     for i = 1, #binary do
  833.         if binary[i] == 1 then
  834.             num = num + powersTwo[bits - i]
  835.         end
  836.     end
  837.  
  838.     return tostring(num)
  839. end
  840.  
  841. local function encodeBigNumbers(numbers)
  842.     for k, v in pairs(numbers) do
  843.         numbers[k] = tostring(v)
  844.     end
  845.     return numbers
  846. end
  847.  
  848. local function stringToBytes(str)
  849.     local result = {}
  850.     for i = 1, #str do
  851.         table.insert(result, string.byte(str, i))
  852.     end
  853.     return result
  854. end
  855.  
  856. local function bytesToString(bytes)
  857.     local str = ""
  858.     for _, v in pairs(bytes) do
  859.         str = str .. string.char(v)
  860.     end
  861.     return str
  862. end
  863.  
  864. local function modexp(base, exponent, modulus)
  865.     local r = 1
  866.  
  867.     while true do
  868.         if exponent % 2 == bigOne then
  869.             r = r * base % modulus
  870.         end
  871.         exponent = exponent / 2
  872.  
  873.         if exponent == bigZero then
  874.             break
  875.         end
  876.         base = base * base % modulus
  877.     end
  878.  
  879.     return r
  880. end
  881.  
  882. local function crypt(key, number)
  883.     local exp
  884.     if key.public then
  885.         exp = bigint(key.public)
  886.     else
  887.         exp = bigint(key.private)
  888.     end
  889.  
  890.     return tostring(modexp(bigint(number), exp, bigint(key.shared)))
  891. end
  892.  
  893. --
  894. -- END OF LIBRARY
  895. --
  896. -- DEMO ENCRYPTION AND DECRYPTION
  897. --
  898.  
  899. local f = io.open("/public.key", "r")
  900. local publicKey = textutils.unserialize(f:read("*a"))
  901. f:close()
  902. f = io.open("/private.key", "r")
  903. local privateKey = textutils.unserialize(f:read("*a"))
  904. f:close()
  905.  
  906. local byteSize = 8
  907. local bits = 256
  908.  
  909. local msg = "hello" -- Maximum message size is bits / byteSize
  910.  
  911. local startTime = os.clock()
  912. -- Encrypting
  913. local res = bytesToNumber(stringToBytes(msg), bits, byteSize)
  914. local encrypted = crypt(publicKey, res)
  915. print("Took " .. os.clock() - startTime .. " seconds to encrypt.")
  916.  
  917. -- You may transmit "encrypted" in public. "encrypted" is a string.
  918.  
  919. sleep(0.1)
  920. startTime = os.clock()
  921. -- Decrypting
  922. local decrypted = crypt(privateKey, encrypted)
  923. local decryptedBytes = numberToBytes(decrypted, bits, byteSize)
  924. print("Took " .. os.clock() - startTime .. " seconds to decrypt.")
  925. print(bytesToString(decryptedBytes))
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement