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

如何在C#中实现与OpenSSL一致的字节转字符打印方式?

DES加密结果直接打印字符与OpenSSL输出不一致的问题与解决

问题描述

重写OpenSSL相关算法时,DES-CBC加密功能验证正常(十六进制/Base64输出与OpenSSL完全匹配),但直接将加密字节打印为字符时,输出与OpenSSL不一致。

命令对比

OpenSSL命令及输出:

echo "foo bar" | openssl des-cbc -K "0123456789ABCDEF" -iv "0123456789ABCDEF" -provider legacy -provider default | xxd
00000000: bcbf 295f 49a1 b714 6469 2be2 99c9 0dcb  ..)_I...di+.....

自定义程序命令及输出:

echo "foo bar" | ./my_openssl des-cbc -k "0123456789ABCDEF" -v "0123456789ABCDEF" | xxd
00000000: efbf bdef bfbd 295f 49ef bfbd efbf bd14  ......)_I.......
00000010: 6469 2bef bfbd efbf bd0d efbf bd         di+..........

当前C#打印代码:

// result 为存储DES-CBC加密结果的byte数组
Console.Write(Encoding.UTF8.GetString(result));

核心原因

加密后的二进制数据并非合法的UTF-8编码,使用Encoding.UTF8.GetString()时,.NET会将无法解析的字节替换为U+FFFD(十六进制EF BF BD),这就是输出差异的来源。

而OpenSSL在默认模式下,直接将原始加密字节写入标准输出,不进行任何编码转换——它输出的是纯二进制数据,而非经过编码的字符。

C#实现方案

要匹配OpenSSL的输出,需直接将字节数组写入标准输出流,跳过字符编码转换:

方法一

using System.IO;

// 直接写入标准输出流
Console.OpenStandardOutput().Write(result, 0, result.Length);
Console.OpenStandardOutput().Flush();

方法二(更简洁)

// 通过Console.Out的基础流写入
Console.Out.BaseStream.Write(result, 0, result.Length);
Console.Out.Flush();

执行上述代码后,输出的二进制字节将与OpenSSL完全一致,再通过xxd查看时就不会出现efbf bd的替换字节。


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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.26 05:55:09