You need to enable JavaScript to run this app.
最新活动
大模型
产品
解决方案
定价
生态与合作
支持与服务
开发者
了解我们

如何在Python Cryptography中读取二进制格式的RSA密钥?

用cryptography加载二进制格式的RSA模数与指数

你之前的问题出在用错了加载函数——load_pem_private_key是专门用来解析PEM格式密钥的,但你手里的是原始二进制的RSA参数(模数、指数),两者格式完全不兼容,自然会报反序列化错误。

下面分公钥和私钥两种情况,给你具体的实现方案:

一、加载RSA公钥(仅模数n+公钥指数e)

RSA公钥只需要模数(n)和公钥指数(e)两个参数,步骤如下:

  1. 把二进制的ne转换成大整数(注意字节序,RSA参数通常用大端字节序存储)
  2. RSAPublicNumbers构造公钥对象

示例代码:

from cryptography.hazmat.primitives.asymmetric import rsa
from cryptography.hazmat.backends import default_backend
from cryptography.hazmat.primitives import serialization

# 假设你从文件读取二进制的模数和指数
with open("public_n.bin", "rb") as f:
    n_bytes = f.read()
with open("public_e.bin", "rb") as f:
    e_bytes = f.read()

# 二进制转大整数(大端字节序)
n = int.from_bytes(n_bytes, byteorder='big')
e = int.from_bytes(e_bytes, byteorder='big')

# 构造公钥
public_numbers = rsa.RSAPublicNumbers(e, n)
public_key = public_numbers.public_key(default_backend())

# 验证:可以导出成PEM格式确认正确性
pem = public_key.public_bytes(
    encoding=serialization.Encoding.PEM,
    format=serialization.PublicFormat.SubjectPublicKeyInfo
)
print(pem.decode())

二、加载RSA私钥(需要更多参数)

私钥的结构比公钥复杂,仅靠模数n和私钥指数d是不够的,还需要质数因子pq,以及三个辅助参数:

  • dmp1 = d % (p-1)
  • dmq1 = d % (q-1)
  • iqmp = pow(q, -1, p) (q的模p逆元)

如果你的二进制文件包含这些参数,代码示例如下:

from cryptography.hazmat.primitives.asymmetric import rsa
from cryptography.hazmat.backends import default_backend
from cryptography.hazmat.primitives import serialization

# 读取所有二进制参数
with open("private_n.bin", "rb") as f:
    n_bytes = f.read()
with open("private_e.bin", "rb") as f:
    e_bytes = f.read()
with open("private_d.bin", "rb") as f:
    d_bytes = f.read()
with open("private_p.bin", "rb") as f:
    p_bytes = f.read()
with open("private_q.bin", "rb") as f:
    q_bytes = f.read()

# 转成大整数
n = int.from_bytes(n_bytes, byteorder='big')
e = int.from_bytes(e_bytes, byteorder='big')
d = int.from_bytes(d_bytes, byteorder='big')
p = int.from_bytes(p_bytes, byteorder='big')
q = int.from_bytes(q_bytes, byteorder='big')

# 计算辅助参数
dmp1 = d % (p - 1)
dmq1 = d % (q - 1)
iqmp = pow(q, -1, p)

# 构造私钥
public_numbers = rsa.RSAPublicNumbers(e, n)
private_numbers = rsa.RSAPrivateNumbers(
    p=p, q=q, d=d,
    dmp1=dmp1, dmq1=dmq1, iqmp=iqmp,
    public_numbers=public_numbers
)
private_key = private_numbers.private_key(default_backend())

# 验证:导出成PEM格式确认正确性
pem = private_key.private_bytes(
    encoding=serialization.Encoding.PEM,
    format=serialization.PrivateFormat.PKCS8,
    encryption_algorithm=serialization.NoEncryption()
)
print(pem.decode())

注意:如果你的二进制文件是把所有参数打包在一起的(比如按顺序存储n、e、d、p、q),需要先按参数的字节长度拆分二进制数据,再分别转换。

内容的提问来源于stack exchange,提问作者drum

火山引擎 最新活动