红帽杯2021 Cryptography

Posted H3rmesk1t

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了红帽杯2021 Cryptography相关的知识,希望对你有一定的参考价值。

红帽杯2021 Cryptography

primegame

这道题搬了一道原题:原题链接
采用的方法为低密度攻击的扩展

题目代码:
from decimal import *
import math
import random
import struct
from flag import flag

assert (len(flag) == 48)
msg1 = flag[:24]
msg2 = flag[24:]                        
primes = [2]
for i in range(3, 90):		# 寻找奇数
    f = True
    for j in primes:
        if i * i < j:
            break
        if i % j == 0:
            f = False
            break
    if f:
        primes.append(i)

getcontext().prec = 100		# 设置浮点数精度
keys = []
for i in range(len(msg1)):
    keys.append(Decimal(primes[i]).ln())

sum_ = Decimal(0.0)
for i, c in enumerate(msg1):
    sum_ += c * Decimal(keys[i])

ct = math.floor(sum_ * 2 ** 256)
print(ct)                  

sum_ = Decimal(0.0)
for i, c in enumerate(msg2):
    sum_ += c * Decimal(keys[i])

ct = math.floor(sum_ * 2 ** 256)
print(ct)	 

该代码的结构如下:
查找不超过100的质数
通过使用flag的前24位与后24位作为随机种子,可以对十进制数组进行混洗
每个改组的素数都表示为ln到Decimal
通过将少量ln值乘以标志的每个字节获得的值相加
题目采用的为背包密码系统,背包加密系统是一种使用0/1背包问题创建的公钥密码系统,流行的攻击方法之一是低密度攻击

exp:
import math
from decimal import *
import random


getcontext().prec = int(100)

primes = [2]
for i in range(3, 90):
    f = True
    for j in primes:
        if i * i < j:
            break
        if i % j == 0:
            f = False
            break
    if f:
        primes.append(i)

keys = []
for i in range(len(primes)):
    keys.append(Decimal(int(primes[i])).ln())

arr = []
for v in keys:
    arr.append(int(v * int(16) ** int(64)))

ct = 425985475047781336789963300910446852783032712598571885345660550546372063410589918
# ct = 597952043660446249020184773232983974017780255881942379044454676980646417087515453

def encrypt(res):
    h = Decimal(int(0))
    for i in range(len(keys)):
        h += res[i] * keys[i]

    ct = int(h * int(16)**int(64))
    return ct


def f(N):
    ln = len(arr)
    A = Matrix(ZZ, ln + 1, ln + 1)
    for i in range(ln):
        A[i, i] = 1
        A[i, ln] = arr[i] // N
        A[ln, i] = 64

    A[ln, ln] = ct // N

    res = A.LLL()

    for i in range(ln + 1):
        flag = True
        for j in range(ln):
            if -64 <= res[i][j] < 64:
                continue
            flag = False
            break
        if flag:
            vec = [int(v + 64) for v in res[i][:-1]]
            ret = encrypt(vec)
            if ret == ct:
                print(N, bytes(vec))


for i in range(2, 10000):
    print(i)
    f(i)

在这里插入图片描述

在这里插入图片描述

分贝将out文件中的ct值放入代码中运行得到flag的两段:b’flag{715c39c3-1b46-4c23-‘和b’8006-27b43eba2446}\\x00\\x00\\x00\\x00\\x00\\x00’

flag为flag{715c39c3-1b46-4c23-8006-27b43eba2446}

hpcurve

这道题也是一道原题改过来的:原题wp链接
我们利用原题的exp,将out文件中的数据放进去直接打

import struct
p = 10000000000000001119

K = GF(p)
R.<x> = K[]; y=x
f = y + prod(map(eval, 'yyyyyyy'))
C = HyperellipticCurve(f, 0)
J = C.jacobian()

def get_u_from_out(output, known_input):
    res = []
    for i in range(24):
        res.append(output[i]^^known_input[i])
    res = bytes(res)
    u0, u1, u2 = struct.unpack("<QQQ", res)
    u = x^3+x^2*u2+x*u1+u0
    return u

from itertools import product

def get_v_from_u(u):
    Kbar = GF(p^6)
    Rbar.<t> = Kbar["t"]
    u2 = u.change_ring(Rbar)
    roots = [x[0] for x in u2.roots()]
    ys = []
    for root in roots:
        ys.append(f(root).sqrt(0,1))
    res = []
    for perm in product(range(2), repeat=3):
        poly = Rbar.lagrange_polynomial([(roots[i], ys[i][perm[i]]) for i in range(3)])
        if poly[0] in K:
            res.append(R(poly))
    return res

def try_decode(output, u, v):
    rs = [u[0], u[1], u[2], v[0], v[1], v[2]]
    otp = struct.pack("<QQQQQQ", *rs)
    plain = []
    for i in range(len(output)):
        plain.append(output[i]^^otp[i%len(otp)])
    return bytes(plain)


output = bytes.fromhex("66def695b20eeae3141ea80240e9bc7138c8fc5aef20532282944ebbbad76a6e17446e92de5512091fe81255eb34a0e22a86a090e25dbbe3141aff0542f5")

known_input = 20*b"a"+b"flag"
u = get_u_from_out(output, known_input)
vs = get_v_from_u(u)
for v in vs:
    print(try_decode(output,u,v))

在这里插入图片描述

运行后得到:flag{1b82f60a-43ab-4f18-8ccc-97d120aae6fc}

flag为flag{1b82f60a-43ab-4f18-8ccc-97d120aae6fc}

以上是关于红帽杯2021 Cryptography的主要内容,如果未能解决你的问题,请参考以下文章

红帽杯2021 Misc

2021红帽杯 framework

红帽杯2021 决赛 opensns 复现

红帽杯2021 决赛 opensns 复现

2021红帽杯 WebsiteManger

2021红帽杯 签到