Certificate Authority - Writeup by AI

Certificate Authority - Writeup by AI

题目信息

  • 来源: Bugku CTF
  • 类别: Crypto (密码学)
  • 考点: 椭圆曲线密码学(ECC)、非标准加密方案、私钥泄露攻击

题目描述

题目提供了一个"非正规"的椭圆曲线加密方案,包含以下文件:

  • p384-key.pem: 包含完整的EC私钥和公钥(使用P-384曲线)
  • ECC.enc: 包含加密算法描述和密文

加密算法

python 复制代码
# 1. 明文分割(flag被分为两部分)
x1 = int(codecs.encode(flag[:12],'hex'),16)  # 前12字节转为大整数
x2 = int(codecs.encode(flag[12:],'hex'),16)  # 剩余部分转为大整数
X = (x1, x2)

# 2. 随机数生成
k = randrange(1, n-1)

# 3. 计算共享点
y0 = k * generator_384  # y0是临时公钥
KPoint = k * PubKey      # KPoint是共享密钥点

# 4. 密文计算(关键!)
Y = (X[0] * KPoint.x() % p, X[1] * KPoint.y() % p)

密文数据

复制代码
Y  = (34113256825339373520369275283701161541979556324226185535033938159804983053982282645600429717939710433082631730889659, 
      32053109834346133043413144503065578404362769943246011698385086926019077101042898269877084920237885778463453847609171)

y0 = (2133726374662399094674717622068093787945171315744414869137518727533960205385423874048257464199675228007664821044234, 
      6814381752433500362278594762998419406730403502594534675593344187219595358988094395062831144664837476184888758539022)

考点分析

考点 权重 说明
PEM文件解析 20% 从PEM格式提取EC私钥和曲线参数
椭圆曲线基础 25% 理解点加法、标量乘法运算
加密方案逆向 30% 分析非标准ECC加密流程
私钥泄露利用 25% 利用已知私钥直接计算共享点

核心漏洞

这是一个自定义的"伪ECC"加密方案,不是标准的ECIES或ElGamal。关键问题在于:

  1. 私钥完全泄露:PEM文件中包含了完整的私钥
  2. 加密方式简单:仅使用模乘混淆,没有哈希派生密钥
  3. 可逆性强:知道私钥即可完全还原共享点KPoint

解题思路

攻击策略

读取PEM私钥文件
提取私钥d和曲线参数
获取密文Y和临时公钥y0
计算KPoint = d * y0
计算模逆元 KPoint.x^-1 mod p
解密: x1 = Y_x * KPoint.x^-1 mod p
同理解密x2
十六进制转字符串得到Flag

关键数学推导

核心发现:虽然不知道随机数k,但可以利用私钥d直接计算KPoint!

复制代码
已知:
  - PubKey = d * G  (d是私钥,G是基点)
  - y0 = k * G      (k是随机数)
  - KPoint = k * PubKey

推导:
  KPoint = k * PubKey
         = k * (d * G)
         = d * (k * G)     ← 椭圆曲线标量乘法满足交换律
         = d * y0          ← 关键!无需知道k

解密公式

python 复制代码
KPoint = d * y0  # 椭圆曲线标量乘法
x1 = Y[0] * inverse(KPoint.x(), p) % p
x2 = Y[1] * inverse(KPoint.y(), p) % p

详细步骤

步骤1: 解析PEM文件提取参数

使用ecdsa库解析PEM文件,提取:

  • 私钥数值 d
  • 曲线参数 (p, a, b, n)
  • 基点 G
  • 公钥点 Q
python 复制代码
import ecdsa

with open('p384-key.pem', 'r') as f:
    pem_content = f.read()

sk = ecdsa.SigningKey.from_pem(pem_content)
private_value = sk.privkey.secret_multiplier

curve = sk.curve
p = curve.curve.p()
a = curve.curve.a()
b = curve.curve.b()
n = curve.order

提取结果

复制代码
私钥 d = 345314803247976874399655422352802886843693493822396778637045222934897919285324680489080513563917526647267225494080206
曲线 p = 39402006196394479212279040100143613805079739270465446667948293404245721771496870329047266088258938001861606973112319
曲线 a = -3
曲线 b = 27580193559959705877849011840389048093056905856361568521428707301988689241309860865136260764883745107765439761230575
阶   n = 39402006196394479212279040100143613805079739270465446667946905279627659399113263569398956308152294913554433653942643

步骤2: 实现椭圆曲线运算

由于这是自定义加密,需要手动实现椭圆曲线点运算:

python 复制代码
class EllipticCurvePoint:
    def __init__(self, x, y, curve_a, curve_p, infinity=False):
        self.x = x
        self.y = y
        self.a = curve_a
        self.p = curve_p
        self.infinity = infinity

def point_add(P, Q):
    """椭圆曲线点加法"""
    if P.infinity: return Q
    if Q.infinity: return P
    
    if P.x == Q.x:
        if P.y != Q.y:
            return EllipticCurvePoint(0, 0, P.a, P.p, infinity=True)
        lam = (3 * P.x * P.x + P.a) * mod_inverse(2 * P.y, P.p) % P.p
    else:
        lam = (Q.y - P.y) * mod_inverse(Q.x - P.x, P.p) % P.p
    
    x_r = (lam * lam - P.x - Q.x) % P.p
    y_r = (lam * (P.x - x_r) - P.y) % P.p
    return EllipticCurvePoint(x_r, y_r, P.a, P.p)

def scalar_multiply(k, P):
    """标量乘法 (double-and-add算法)"""
    result = EllipticCurvePoint(0, 0, P.a, P.p, infinity=True)
    addend = P
    while k:
        if k & 1:
            result = point_add(result, addend)
        addend = point_add(addend, addend)
        k >>= 1
    return result

步骤3: 计算共享点KPoint

利用私钥d和临时公钥y0计算:

python 复制代码
y0_point = EllipticCurvePoint(y0_x, y0_y, a, p)
KPoint = scalar_multiply(private_value, y0_point)

# 结果:
# KPoint.x = 18835199024416865644365965566902449266278348711722870356856651542135605633788994751183739828403791317654420216560817
# KPoint.y = 11558519284930642642341208101507709758464537415633959470643930313232338707486127894445738639245491232995442111490098

步骤4: 解密明文

计算模逆元并恢复x1和x2:

python 复制代码
KPoint_x_inv = mod_inverse(KPoint.x, p)
KPoint_y_inv = mod_inverse(KPoint.y, p)

x1 = (Y_x * KPoint_x_inv) % p  # 31698494968736568155583361887
x2 = (Y_y * KPoint_y_inv) % p  # 26445730285019478715091403133

步骤5: 转换为Flag

将大整数转换回十六进制再解码为字符串:

python 复制代码
hex_x1 = hex(x1)[2:]  # '18e7e5c5f5f33'
hex_x2 = hex(x2)[2:]  # '142a5e3766315'

# 补齐偶数长度
if len(hex_x1) % 2 != 0: hex_x1 = '0' + hex_x1
if len(hex_x2) % 2 != 0: hex_x2 = '0' + hex_x2

flag_part1 = codecs.decode(hex_x1, 'hex').decode('utf-8')  # 'flag{3CC_I3_'
flag_part2 = codecs.decode(hex_x2, 'hex').decode('utf-8')  # 'Use7f1_HaHA}'

flag = flag_part1 + flag_part2  # 'flag{3CC_I3_Use7f1_HaHA}'

运行结果

复制代码
============================================================
Certificate Authority - ECC解密
============================================================

✓ 成功使用ecdsa库解析PEM
  曲线参数:
    p = 39402006196394479212279040100143613805079739270465446667948293404245721771496870329047266088258938001861606973112319
    a = -3
    b = 27580193559959705877849011840389048093056905856361568521428707301988689241309860865136260764883745107765439761230575
    n = 39402006196394479212279040100143613805079739270465446667946905279627659399113263569398956308152294913554433653942643
  私钥 d = 345314803247976874399655422352802886843693493822396778637045222934897919285324680489080513563917526647267225494080206
  公钥 Q = (206472480816501406837281388996335457607609068965647575006464669330299894293999634147080012252011563534842054211995280, 271284199742960113939785931274188966364076177927911299446156024948916655234077123509433666197034008248433960277493512)

[步骤2] 加载密文数据...
  Y = (34113256825339373520369275283701161541979556324226185535033938159804983053982282645600429717939710433082631730889659, 
       32053109834346133043413144503065578404362769943246011698385086926019077101042898269877084920237885778463453847609171)
  y0 = (2133726374662399094674717622068093787945171315744414869137518727533960205385423874048257464199675228007664821044234, 
        6814381752433500362278594762998419406730403502594534675593344187219595358988094395062831144664837476184888758539022)

[步骤3] 计算共享点 KPoint = d * y0...
  KPoint = (18835199024416865644365965566902449266278348711722870356856651542135605633788994751183739828403791317654420216560817, 
            11558519284930642642341208101507709758464537415633959470643930313232338707486127894445738639245491232995442111490098)

[步骤4] 解密明文...
  x1 = 31698494968736568155583361887
  x2 = 26445730285019478715091403133

[步骤5] 转换为flag字符串...
  Flag部分1 (前12字节): 'flag{3CC_I3_'
  Flag部分2 (剩余): 'Use7f1_HaHA}'

============================================================
完整Flag: flag{3CC_I3_Use7f1_HaHA}
============================================================

✓ 解密成功!
相关推荐
fengci.1 小时前
CTF+随机困难部分
android·开发语言·网络·安全·php
随身数智备忘录1 小时前
安全巡检执行率能解决哪些场景痛点?一套安全巡检执行率提升方案实战
安全
其实防守也摸鱼1 小时前
Upload-labs:部署靶场及Pass-01实战解析
服务器·网络·安全·web安全·教程·文件上传·工具
菱玖2 小时前
等保2.0及其测评
网络·安全·web安全
数字护盾(和中)2 小时前
终端安全破局:银狐木马防御的 EDR 核心能力详解
网络·人工智能·安全
团象科技2 小时前
合规收紧,出海云账号如何稳、准、安全落地?
安全
caijing3652 小时前
全方位解析建筑设备系统解决方案:提升建筑效率与安全的关键
大数据·人工智能·安全
智塑未来2 小时前
高精度3D室内定位设备如何赋能机器人科研创新
人工智能·安全
步步为营DotNet3 小时前
深入探究.NET 11中的 Native AOT 性能优化与实践
安全·云原生·.net