rapid7/metasploit-framework

View on GitHub
data/meterpreter/python/met_rsa.py

Summary

Maintainability
A
1 hr
Test Coverage
import sys
import math
import random
import binascii as ba
import os
from struct import unpack as u
from struct import pack
is2 = sys.version_info[0] < 3


def bt(b):
    if is2:
        return b
    return ord(b)


def b2i(b):
    return int(ba.b2a_hex(b), 16)


def i2b(i):
    h = '%x' % i
    if len(h) % 2 == 1:
        h = '0' + h
    if not is2:
        h = h.encode('utf-8')
    return ba.a2b_hex(h)


def rs(a, o):
    if a[o] == bt(pack('B', 0x81)):
        return (u('B', a[o + 1])[0], 2 + o)
    elif a[o] == bt(pack('B', 0x82)):
        return (u('>H', a[o + 1:o + 3])[0], 3 + o)


def ri(b, o):
    i, o = rs(b, o)
    return (b[o:o + i], o + i)


def b2me(b):
    if b[0] != bt(pack('B', 0x30)):
        return (None, None)
    _, o = rs(b, 1)
    if b[o] != bt(pack('B', 2)):
        return (None, None)
    (m, o) = ri(b, o + 1)
    if b[o] != bt(pack('B', 2)):
        return (None, None)
    e = b[o + 2:]
    return (b2i(m), b2i(e))


def der2me(d):
    if d[0] != bt(pack('B', 0x30)):
        return (None, None)
    _, o = rs(d, 1)
    while o < len(d):
        if d[o] == bt(pack('B', 0x30)):
            o += u('B', d[o + 1:o + 2])[0]
        elif d[o] == bt(pack('B', 0x05)):
            o += 2
        elif d[o] == bt(pack('B', 0x03)):
            _, o = rs(d, o + 1)
            return b2me(d[o + 1:])
        else:
            return (None, None)


def rsa_enc(der, msg):
    m, e = der2me(der)
    h = pack('BB', 0, 2)
    d = pack('B', 0)
    l = 256 - len(h) - len(msg) - len(d)
    p = os.urandom(512).replace(pack('B', 0), pack(''))
    return i2b(pow(b2i(h + p[:l] + d + msg), e, m))