c# - 复制加密算法

标签 c# algorithm delphi encryption aes

(我尝试在 Cryptography Stack Exchange 上询问这个问题,但他们认为在那里不合适。)

我正在尝试在 C# 中复制用 Delphi 编写的算法,最好使用标准 .NET 库。据推测,Delphi 算法通过了标准引用测试。应该是AES/CBC;但是,我无法使用 System.Security.Cryptography.AesManaged 复制结果。

简单输入调用示例:

function StringToHex(S: string): string;
var
  i: integer;
begin
  Result := '';
  for i := 1 to Length(S) do
    Result := Result + IntToHex(Ord(S[i]), 2);
end;

var
  PlainText:     AnsiString;
  AES:           TAES;
  Key:           TAESKey256;  // array[0..31] of byte;
  InitialVector: TAESBuffer;  // array[0..15] of byte;
  InputStream:   TStringStream;
  OutputStream:  TStringStream;

begin
  PlainText := 'test';
  FillChar(Key, SizeOf(Key), 1);
  FillChar(InitialVector, SizeOf(InitialVector), 2);

  AES          := TAES.Create;
  InputStream  := TStringStream.Create(PlainText);
  OutputStream := TStringStream.Create('');

  try
    AES.EncryptAESStreamCBC(InputStream, 0, Key, InitialVector, OutputStream);

    Writeln(StringToHex(OutputStream.DataString));
    Readln;
  finally
    InputStream.Free;
    OutputStream.Free;
    AES.Free;
  end;
end.

输出:

CEE3684F05D02E5A0930CED21F76075A

代码似乎是基于 Delphi Spring Framework .

我如何在 .NET 中复制它?

我尝试过的方法(甚至切换到字节以避免任何 Unicode 问题):

public byte[] Encrypt()
{
    using (var algorithm = new AesManaged())
    {
        // Default is CBC
        algorithm.Key = Enumerable.Repeat((byte)0x01, 32).ToArray();
        algorithm.IV = Enumerable.Repeat((byte)0x02, 16).ToArray();

        using (ICryptoTransform encryptor = algorithm.CreateEncryptor(algorithm.Key, algorithm.IV))
        {
            using (var stream = new MemoryStream())
            {
                using (var cryptoStream = new CryptoStream(stream, encryptor, CryptoStreamMode.Write))
                {
                    using (var writer = new BinaryWriter(cryptoStream))
                    {
                        writer.Write(new byte[] {0x74, 0x65, 0x73, 0x74});
                    }
                    return stream.ToArray();
                }
            }
        }
    }
}

虽然这会导致不同的输出(第一个字节是 x6D)。

最佳答案

在其他任务中提到了 c# 的默认设置:

BlockSize = 128;
Mode = System.Security.Cryptography.CipherMode.CBC;
Padding = System.Security.Cryptography.PaddingMode.PKCS7

在 Delphi 中,我看不到任何更改 PaddingMode 的选项,我猜它用零填充。 如果正确,则应将 C# 中的填充切换为

System.Security.Cryptography.PaddingMode.Zeros

(抱歉,无法验证,这只是假设)。

更新:顺便提一句,它有效,只需添加一行:

algorithm.Padding = PaddingMode.Zeros;

关于c# - 复制加密算法,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/23788606/

相关文章:

delphi - 将 SQL Server 查询转换为 Delphi 语法

json - Delphi 中的自定义编码 TDictionary

c# - 在 C# 或 C++ 上从 Internet 获取和解析网页

c# - 如何在 C#.Net 中处理来自 Webservice 的海量 JSON 数据

java - 给定根节点和目标节点的二叉树之和是多少?

algorithm - 拓扑排序,但具有某种分组

algorithm - Knuth-Morris-Pratt 算法中的冗余指令

for 循环内的 C# 查询仅返回一个值

c# - 将 SQL DB 部署到 Azure 超时启用索引

delphi - 使用 StringList :\n vs #13#10 vs sLineBreak 解析文本