Ejemplo n.º 1
0
def crypto_scalarmult_curve25519_tweet(q, n, p):
    '''int crypto_scalarmult_curve25519_tweet(u8*q, const u8*n, const u8*p)'''
    z = IntArray(u8, size=32)
    x = IntArray(i64, size=80)
    r = i64()

    a = gf()
    b = gf()
    c = gf()
    d = gf()
    e = gf()
    f = gf()

    for i in range(31):
        z[i] = n[i]
    z[31] = (n[31] & 127) | 64
    z[0] &= 248

    unpack25519(x, p)

    for i in range(16):
        b[i] = x[i]
        d[i] = a[i] = c[i] = 0

    a[0] = d[0] = 1
    for i in range(254, -1, -1):
        r = (z[i >> 3] >> (i & 7)) & 1
        sel25519(a, b, r)
        sel25519(c, d, r)
        A(e, a, c)
        Z(a, a, c)
        A(c, b, d)
        Z(b, b, d)
        S(d, e)
        S(f, a)
        M(a, c, a)
        M(c, b, e)
        A(e, a, c)
        Z(a, a, c)
        S(b, a)
        Z(c, d, f)
        M(a, c, _121665)
        A(a, a, d)
        M(c, c, a)
        M(a, d, f)
        M(d, b, x)
        S(b, e)
        sel25519(a, b, r)
        sel25519(c, d, r)

    for i in range(16):
        x[i + 16] = a[i]
        x[i + 32] = c[i]
        x[i + 48] = b[i]
        x[i + 64] = d[i]

    x[32:] = inv25519(x[32:], x[32:])
    x[16:] = M(x[16:], x[16:], x[32:])
    pack25519(q, x[16:])
    return 0
Ejemplo n.º 2
0
def crypto_stream_salsa20_tweet_xor(c, m, b, n, k):
    '''int crypto_stream_salsa20_tweet_xor(u8*c, const u8*m, u64 b, const u8*n, const u8*k)'''
    z = IntArray(u8, size=16)
    x = IntArray(u8, size=64)

    if not b: return 0

    for i in range(8):
        z[i] = n[i]

    c_off = 0
    m_off = 0
    while b >= 64:
        crypto_core_salsa20_tweet(x, z, k, sigma)
        for i in range(64):
            c[i + c_off] = (m[i + m_off] if m else 0) ^ x[i]
        u = u32(1)
        for i in range(8, 16):
            u += u32(z[i])
            z[i] = u
            u >>= 8
        b -= 64
        c_off += 64
        if m: m_off += 64

    if b:
        crypto_core_salsa20_tweet(x, z, k, sigma)
        for i in range(b):
            c[i + c_off] = (m[i + m_off] if m else 0) ^ x[i]

    return 0
Ejemplo n.º 3
0
def crypto_hash_sha512_tweet(out, m, n):
    '''int crypto_hash_sha512_tweet(u8*out, const u8*m, u64 n)'''
    h = IntArray(u8, size=64)
    x = IntArray(u8, size=256)
    b = u64(n)

    for i in range(64):
        h[i] = iv[i]

    crypto_hashblocks_sha512_tweet(h, m, n)
    m_off = n
    n &= 127
    m_off -= n

    x[:256] = 256 * [u8()]
    for i in range(n):
        x[i] = m[i + m_off]
    x[n] = 128

    n = 256 - 128 * (n < 112)
    x[n - 9] = b >> 61
    x[n - 8:] = ts64(x[n - 8:], b << 3)
    crypto_hashblocks_sha512_tweet(h, x, n)

    for i in range(64):
        out[i] = h[i]

    return 0
Ejemplo n.º 4
0
def neq25519(a, b):
    '''int neq25519(const gf a, const gf b)'''
    c = IntArray(u8, size=32)
    d = IntArray(u8, size=32)
    pack25519(c, a)
    pack25519(d, b)
    return crypto_verify_32_tweet(c, d)
Ejemplo n.º 5
0
def reduce(r):
    '''void reduce(u8*r)'''
    x = IntArray(i64, size=64)
    for i in range(64):
        x[i] = u64(r[i])
    r[:64] = 64 * [u8()]
    modL(r, x)
Ejemplo n.º 6
0
def crypto_sign_ed25519_tweet(sm, smlen, m, n, sk):
    '''int crypto_sign_ed25519_tweet(u8*sm, u64*smlen, const u8*m, u64 n, const u8*sk)'''
    d = IntArray(u8, size=64)
    h = IntArray(u8, size=64)
    r = IntArray(u8, size=64)
    x = IntArray(i64, size=64)
    p = [gf() for i in range(4)]

    crypto_hash_sha512_tweet(d, sk, 32)
    d[0] &= 248
    d[31] &= 127
    d[31] |= 64

    # There is no (simple?) way to return this argument's value back to the
    # user in python.  Rather than redefining the return value of this function
    # it is better to advise the user that ``smlen`` does not work as it does
    # in the C implementation and that its value will be equal to ``n + 64``.
    smlen = n + 64
    for i in range(n):
        sm[64 + i] = m[i]
    for i in range(32):
        sm[32 + i] = d[32 + i]

    crypto_hash_sha512_tweet(r, sm[32:], n + 32)
    reduce(r)
    scalarbase(p, r)
    pack(sm, p)

    for i in range(32):
        sm[i + 32] = sk[i + 32]
    crypto_hash_sha512_tweet(h, sm, n + 64)
    reduce(h)

    for i in range(64):
        x[i] = 0
    for i in range(32):
        x[i] = u64(r[i])
    for i in range(32):
        for j in range(32):
            x[i + j] += h[i] * u64(d[j])
    sm[32:] = modL(sm[32:], x)

    return 0
Ejemplo n.º 7
0
def crypto_secretbox_xsalsa20poly1305_tweet_open(m, c, d, n, k):
    '''int crypto_secretbox_xsalsa20poly1305_tweet_open(u8*m, const u8*c, u64 d, const u8*n, const u8*k)'''
    x = IntArray(u8, size=32)
    if d < 32: return -1
    crypto_stream_xsalsa20_tweet(x, 32, n, k)
    if crypto_onetimeauth_poly1305_tweet_verify(c[16:], c[32:], d - 32,
                                                x) != 0:
        return -1
    crypto_stream_xsalsa20_tweet_xor(m, c, d, n, k)
    m[:32] = 32 * [u8()]
    return 0
Ejemplo n.º 8
0
def core(out, in_, k, c, h):
    '''void core(u8*out, const u8*in, const u8*k, const u8*c, int h)'''
    w = IntArray(u32, size=16)
    x = IntArray(u32, size=16)
    y = IntArray(u32, size=16)
    t = IntArray(u32, size=4)

    for i in range(4):
        x[5 * i] = ld32(c[4 * i:])
        x[1 + i] = ld32(k[4 * i:])
        x[6 + i] = ld32(in_[4 * i:])
        x[11 + i] = ld32(k[16 + 4 * i:])

    for i in range(16):
        y[i] = x[i]

    for i in range(20):
        for j in range(4):
            for m in range(4):
                t[m] = x[(5 * j + 4 * m) % 16]
            t[1] ^= L32(t[0] + t[3], 7)
            t[2] ^= L32(t[1] + t[0], 9)
            t[3] ^= L32(t[2] + t[1], 13)
            t[0] ^= L32(t[3] + t[2], 18)
            for m in range(4):
                w[4 * j + (j + m) % 4] = t[m]
        for m in range(16):
            x[m] = w[m]

    if h:
        for i in range(16):
            x[i] += y[i]
        for i in range(4):
            x[5 * i] -= ld32(c[4 * i:])
            x[6 + i] -= ld32(in_[4 * i:])
        for i in range(4):
            out[4 * i:] = st32(out[4 * i:], x[5 * i])
            out[16 + 4 * i:] = st32(out[16 + 4 * i:], x[6 + i])
    else:
        for i in range(16):
            out[4 * i:] = st32(out[4 * i:], x[i] + y[i])
Ejemplo n.º 9
0
def crypto_hashblocks_sha512_tweet(x, m, n):
    '''int crypto_hashblocks_sha512_tweet(u8*x, const u8*m, u64 n)'''
    z = IntArray(u64, size=8)
    b = IntArray(u64, size=8)
    a = IntArray(u64, size=8)
    w = IntArray(u64, size=16)
    t = u64()

    for i in range(8):
        z[i] = a[i] = dl64(x[8 * i:])

    m_off = 0
    while n >= 128:
        for i in range(16):
            w[i] = dl64(m[8 * i + m_off:])

        for i in range(80):
            for j in range(8):
                b[j] = a[j]
            t = a[7] + Sigma1(a[4]) + Ch(a[4], a[5], a[6]) + K[i] + w[i % 16]
            b[7] = t + Sigma0(a[0]) + Maj(a[0], a[1], a[2])
            b[3] += t

            for j in range(8):
                a[(j + 1) % 8] = b[j]
            if i % 16 == 15:
                for j in range(16):
                    w[j] += w[(j + 9) % 16] + sigma0(w[(j + 1) % 16]) + sigma1(
                        w[(j + 14) % 16])

        for i in range(8):
            a[i] += z[i]
            z[i] = a[i]

        m_off += 128
        n -= 128

    for i in range(8):
        x[8 * i:] = ts64(x[8 * i:], z[i])

    return n
Ejemplo n.º 10
0
def crypto_sign_ed25519_tweet_open(m, mlen, sm, n, pk):
    '''int crypto_sign_ed25519_tweet_open(u8*m, u64*mlen, const u8*sm, u64 n, const u8*pk)'''
    t = IntArray(u8, size=32)
    h = IntArray(u8, size=64)
    p = [gf() for i in range(4)]
    q = [gf() for i in range(4)]

    mlen = -1
    if n < 64: return -1

    if unpackneg(q, pk): return -1

    for i in range(n):
        m[i] = sm[i]
    for i in range(32):
        m[i + 32] = pk[i]
    crypto_hash_sha512_tweet(h, m, n)
    reduce(h)
    scalarmult(p, q, h)

    scalarbase(q, sm[32:])
    add(p, q)
    pack(t, p)

    n -= 64
    if crypto_verify_32_tweet(sm, t):
        for i in range(n):
            m[i] = 0
        return -1

    for i in range(n):
        m[i] = sm[i + 64]
    # There is no (simple?) way to return this argument's value back to the
    # user in python.  Rather than redefining the return value of this function
    # it is better to advise the user that ``mlen`` does not work as it does in
    # the C implementation and that its value will be equal to ``-1`` if ``n <
    # 64`` or decryption fails and ``n - 64`` otherwise.
    mlen = n
    return 0
Ejemplo n.º 11
0
def M(o, a, b):
    '''void M(gf o, const gf a, const gf b)'''
    t = IntArray(i64, size=31)
    for i in range(16):
        for j in range(16):
            t[i + j] += a[i] * b[j]
    for i in range(15):
        t[i] += 38 * t[i + 16]
    for i in range(16):
        o[i] = t[i]

    car25519(o)
    car25519(o)

    return o
Ejemplo n.º 12
0
def crypto_sign_ed25519_tweet_keypair(pk, sk):
    '''int crypto_sign_ed25519_tweet_keypair(u8*pk, u8*sk)'''
    d = IntArray(u8, size=64)
    p = [gf() for i in range(4)]

    randombytes(sk, 32)
    crypto_hash_sha512_tweet(d, sk, 32)
    d[0] &= 248
    d[31] &= 127
    d[31] |= 64

    scalarbase(p, d)
    pack(pk, p)

    for i in range(32):
        sk[32 + i] = pk[i]
    return 0
Ejemplo n.º 13
0
def crypto_box_curve25519xsalsa20poly1305_tweet_open(m, c, d, n, y, x):
    '''int crypto_box_curve25519xsalsa20poly1305_tweet_open(u8*m, const u8*c, u64 d, const u8*n, const u8*y, const u8*x)'''
    k = IntArray(u8, size=32)
    crypto_box_curve25519xsalsa20poly1305_tweet_beforenm(k, y, x)
    return crypto_box_curve25519xsalsa20poly1305_tweet_open_afternm(
        m, c, d, n, k)
Ejemplo n.º 14
0
def crypto_box_curve25519xsalsa20poly1305_tweet_beforenm(k, y, x):
    '''int crypto_box_curve25519xsalsa20poly1305_tweet_beforenm(u8*k, const u8*y, const u8*x)'''
    s = IntArray(u8, size=32)
    crypto_scalarmult_curve25519_tweet(s, x, y)
    return crypto_core_hsalsa20_tweet(k, _0, s, sigma)
Ejemplo n.º 15
0
 def __init__(self, init=()):
     IntArray.__init__(self, i64, init=init, size=16)
Ejemplo n.º 16
0
def crypto_stream_salsa20_tweet(c, d, n, k):
    '''int crypto_stream_salsa20_tweet(u8*c, u64 d, const u8*n, const u8*k)'''
    return crypto_stream_salsa20_tweet_xor(c, IntArray(u8), d, n, k)
Ejemplo n.º 17
0
def crypto_stream_xsalsa20_tweet_xor(c, m, d, n, k):
    '''int crypto_stream_xsalsa20_tweet_xor(u8*c, const u8*m, u64 d, const u8*n, const u8*k)'''
    s = IntArray(u8, size=32)
    crypto_core_hsalsa20_tweet(s, n, k, sigma)
    return crypto_stream_salsa20_tweet_xor(c, m, d, n[16:], s)
Ejemplo n.º 18
0
def crypto_onetimeauth_poly1305_tweet_verify(h, m, n, k):
    '''int crypto_onetimeauth_poly1305_tweet_verify(const u8*h, const u8*m, u64 n, const u8*k)'''
    x = IntArray(u8, size=16)
    crypto_onetimeauth_poly1305_tweet(x, m, n, k)
    return crypto_verify_16_tweet(h, x)
Ejemplo n.º 19
0
def crypto_onetimeauth_poly1305_tweet(out, m, n, k):
    '''int crypto_onetimeauth_poly1305_tweet(u8*out, const u8*m, u64 n, const u8*k)'''
    s = u32()
    u = u32()
    x = IntArray(u32, size=17)
    r = IntArray(u32, size=17)
    h = IntArray(u32, size=17)
    c = IntArray(u32, size=17)
    g = IntArray(u32, size=17)

    for j in range(16):
        r[j] = k[j]
    r[3] &= 15
    r[4] &= 252
    r[7] &= 15
    r[8] &= 252
    r[11] &= 15
    r[12] &= 252
    r[15] &= 15

    while n > 0:
        c[:17] = 17 * [u32()]
        for j in range(16):
            if j >= n:
                j -= 1
                break
            c[j] = m[j]
        j += 1
        c[j] = 1
        m = m[j:]
        n -= j
        add1305(h, c)

        for i in range(17):
            x[i] = 0
            for j in range(17):
                x[i] += h[j] * (r[i - j] if j <= i else 320 * r[i + 17 - j])

        for i in range(17):
            h[i] = x[i]
        u = 0

        for j in range(16):
            u += h[j]
            h[j] = u & 255
            u >>= 8

        u += h[16]
        h[16] = u & 3
        u = 5 * (u >> 2)

        for j in range(16):
            u += h[j]
            h[j] = u & 255
            u >>= 8

        u += h[16]
        h[16] = u

    for j in range(17):
        g[j] = h[j]
    add1305(h, minusp)
    s = -(h[16] >> 7)
    for j in range(17):
        h[j] ^= s & (g[j] ^ h[j])

    for j in range(16):
        c[j] = k[j + 16]
    c[16] = 0
    add1305(h, c)
    for j in range(16):
        out[j] = h[j]

    return 0
Ejemplo n.º 20
0
def par25519(a):
    '''u8 par25519(const gf a)'''
    d = IntArray(u8, size=32)
    pack25519(d, a)
    return d[0] & 1
Ejemplo n.º 21
0
class gf(IntArray):
    def __init__(self, init=()):
        IntArray.__init__(self, i64, init=init, size=16)


def randombytes(c, s):
    '''
    insert s random bytes into c
    '''
    if lt_py3:
        c[:s] = bytearray(os.urandom(s))
    else:
        c[:s] = os.urandom(s)


_0 = IntArray(u8, size=16)
_9 = IntArray(u8, size=32, init=[9])

gf0 = gf()
gf1 = gf([1])
_121665 = gf([0xDB41, 1])
D = gf([
    0x78a3, 0x1359, 0x4dca, 0x75eb, 0xd8ab, 0x4141, 0x0a4d, 0x0070, 0xe898,
    0x7779, 0x4079, 0x8cc7, 0xfe73, 0x2b6f, 0x6cee, 0x5203
])
D2 = gf([
    0xf159, 0x26b2, 0x9b94, 0xebd6, 0xb156, 0x8283, 0x149a, 0x00e0, 0xd130,
    0xeef3, 0x80f2, 0x198e, 0xfce7, 0x56df, 0xd9dc, 0x2406
])
X = gf([
    0xd51a, 0x8f25, 0x2d60, 0xc956, 0xa7b2, 0x9525, 0xc760, 0x692c, 0xdc5c,