You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

基于AES算法的图片加解密报错:密钥长度不正确(64字节)

问题解决:AES密钥长度错误(64字节)

问题原因

AES算法仅支持**16字节(128位)、24字节(192位)、32字节(256位)**的密钥长度。你的代码中通过hashlib.sha256(...).hexdigest()生成的是64个字符的字符串(64字节),不符合AES的密钥要求,因此触发错误。

修复方案

1. 修正密钥生成逻辑

将哈希结果从十六进制字符串(hexdigest)改为原始字节串(digest),sha256的原始哈希值正好是32字节,符合AES-256的密钥长度要求。

修改image_open和cipher_open函数中的密钥生成代码:

# 原代码
password = hashlib.sha256(enc_pass.encode('utf-8')).hexdigest()

# 修改后
password = hashlib.sha256(enc_pass.encode('utf-8')).digest()

2. 修复解密函数的语法错误

解密函数中有一行代码缺少右括号,导致运行报错:

# 原代码
decrypted = decrypted.replace("n",""

# 修改后
decrypted = decrypted.replace("n", "")

3. 可选优化:使用随机IV(增强安全性)

当前代码使用固定IV'This is an IV456',虽然能运行,但固定IV会降低加密安全性。建议生成随机IV并随密文一起存储,示例如下:

# 加密时生成随机IV
iv = os.urandom(16)
obj = AES.new(password, AES.MODE_CBC, iv)
# 将IV写入密文文件开头
g = open(cipher_name, 'wb')
g.write(iv)
g.write(ciphertext)

# 解密时读取IV
cipher = open(ciphername, 'rb')
iv = cipher.read(16)
ciphertext = cipher.read()
obj2 = AES.new(password, AES.MODE_CBC, iv)

完整修改后的关键代码片段

加密按钮事件

def image_open():
    global file_path_e

    enc_pass = passg.get()
    if enc_pass == "":
        pass_alert()
    else:
        # 改用digest获取32字节原始哈希
        password = hashlib.sha256(enc_pass.encode('utf-8')).digest()
        filename = filedialog.askopenfilename()
        file_path_e = os.path.dirname(filename)
        encrypt(filename,password)

解密按钮事件

def cipher_open():
    global file_path_d

    dec_pass = passg.get()
    if dec_pass == "":
        pass_alert()
    else:
        # 改用digest获取32字节原始哈希
        password = hashlib.sha256(dec_pass.encode('utf-8')).digest()
        filename = filedialog.askopenfilename()
        file_path_d = os.path.dirname(filename)
        decrypt(filename,password)

修复后的解密函数

def decrypt(ciphername,password):
    secret_image = Image.open("secret.jpeg")
    ima = Image.open("2-share_encrypt.jpeg")
    new_image = generate_image_back(secret_image, ima)
    new_image.save("2-share_decrypt.jpeg")
    print("2-share Decryption done....")
    
    # 用二进制模式读取密文,避免编码问题
    cipher = open(ciphername,'rb')
    ciphertext = cipher.read()

    # 解密密文
    obj2 = AES.new(password, AES.MODE_CBC, b'This is an IV456')
    decrypted = obj2.decrypt(ciphertext).decode('utf-8')

    # 修复语法错误:添加右括号
    decrypted = decrypted.replace("n", "")

    # 提取图像尺寸
    newwidth = decrypted.split("w")[1]
    newheight = decrypted.split("h")[1]

    # 移除尺寸标记
    heightr = "h" + str(newheight) + "h"
    widthr = "w" + str(newwidth) + "w"
    decrypted = decrypted.replace(heightr,"")
    decrypted = decrypted.replace(widthr,"")

    # 重建像素数组
    step = 3
    finaltextone=[decrypted[i:i+step] for i in range(0, len(decrypted), step)]
    finaltexttwo=[(int(finaltextone[int(i)])-100,int(finaltextone[int(i+1)])-100,int(finaltextone[int(i+2)])-100) for i in range(0, len(finaltextone), step)]

    # 生成解密后的图像
    newim = Image.new("RGB", (int(newwidth), int(newheight)))
    newim.putdata(finaltexttwo)
    newim.save("visual_decrypt.jpeg")
    print("Visual Decryption done......")

注意:读取和写入密文时建议使用二进制模式('rb'/'wb'),避免字符编码问题导致密文损坏。

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

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.22 21:59:52