Aes
AES 輸出長度並不總是 16 的倍數
我有一個 C# 解決方案,它使用 AES 加密一堆小數據塊。
//This is how I'm configuring the Aes object var aes = Aes.Create(); aes.Mode = CipherMode.CBC; aes.KeySize = 256; aes.Padding = PaddingMode.PKCS7;
然後我將原始密文字節寫入 SQL Server VARBINARY 列。
查詢這些 VARBINARY 密文列的長度,我希望它們始終是 16 個字節的倍數。然而,這裡的情況似乎並非如此。
我試著在網上閱讀它,我發現的唯一問題是問為什麼 AES 密文被填充到 16 字節塊,所以我想我會在這裡問反問題。
筆記:
- 我測試了解密這些奇怪大小的密文之一,它工作正常,所以密文沒有格式錯誤。
- 我注意到它並不經常發生,在一次執行中,它在 5,828 次中發生了 19 次。
- 當它確實發生時,它總是一個接一個(31 而不是 32,767 而不是 768,等等..)
我有一個想法,也許 AES 標準可能會從輸出的末尾截斷恰好為零(或其他一些眾所周知的數字)的密碼字節,因為它可以由解密器重建?但希望澄清。
好的,正如其他人所指出的那樣,該標準始終會生成長度為 16 個字節的倍數的密文。問題是當我測量長度時,我使用了 T-SQL LEN 函式,它在測量長度時似乎從二進制序列的末尾修剪了 0x20 字節。
我現在了解到我應該使用不進行此修剪的 DATALENGTH 函式,並且當我嘗試它時,所有值都是 16 的倍數。
為混亂道歉!
你是對的; 標準 AES-CBC(沒有密文竊取)的輸出長度始終是 16 字節的倍數。
我想到的一種可能性是,如果您的 AES 實現有故障,如果最後一個字節恰好是 0x00,那麼它實際上不會輸出它(並且在解密方向上,如果密文短一個字節,它會隱式添加 0x00)。
如果這個假設成立,那麼在您的 5,828 個測試案例中,我們期望看到最後一個密文字節為 0(因此被截斷)預期的 22.8 倍;19 次正好在標準偏差之內,所以這是合理的……