Openssl

OpenSSL - 從簽名數據中提取雜湊算法(PKCS#1 v 1.5)

  • September 28, 2021

PKCS#1 v 1.5 儲存用於消化原始消息的雜湊算法標識符。我想知道是否以及如何提取此資訊。

我正在處理一個包含簽名字節的緩衝區和一個帶有公鑰的緩衝區。

我知道它可以完成(例如 openssl rsautl 使用 -verify 和 -asn1parse 完成),但在 openssl 中沒有關於 asn1 函式的合理文件。

給定RSASSA-PKCS1-v1_5簽名的雜湊標識符只能使用簽名的公鑰¹獲得。它是通過執行簽名驗證步驟 1 和 2/a/b/c 來揭示的(基本上將簽名作為整數,將其提升到冪 $ e $ 模組 $ N $ 從公鑰中提取,並轉換回字節),然後解析編碼消息,這應該按照第 9.2 節的步驟 5進行,即 $$ \text{EM}=\mathtt{00}\mathbin|\mathtt{01}\mathbin|\mathtt{FF}\mathbin|\ldots|\mathtt{FF}\mathbin|\mathtt{00}\mathbin|T $$ 在哪裡

  • 左邊兩個字節 $ \mathtt{00}\mathbin|\mathtt{01} $ 是固定的,然後是 $ f\ge8 $ 字節在 $ \mathtt{FF} $ 然後一個 $ \mathtt{00} $ ( $ f $ 是最大的,即對於 $ b $ -bit 公共模數 $ N $ 的長度 $ T $ 是 $ \left\lfloor(b-17)/8\right\rfloor-f $ 字節)。
  • $ T $ 是 ASN.1 DER 編碼,包含雜湊標識符和雜湊值。

實用的解碼方法 $ T $ 是看註釋1(或下表,來自該註釋)。

MD2:         30 20 30 0C 06 08 2A 86 48 86 F7 0D 02 02 05 00 04 10 ∥ H
MD5:         30 20 30 0C 06 08 2A 86 48 86 F7 0D 02 05 05 00 04 10 ∥ H
SHA-1:       30 21 30 09 06 05 2B 0E 03 02 1A 05 00 04 14 ∥ H
SHA-224:     30 2D 30 0D 06 09 60 86 48 01 65 03 04 02 04 05 00 04 1C ∥ H
SHA-256:     30 31 30 0D 06 09 60 86 48 01 65 03 04 02 01 05 00 04 20 ∥ H
SHA-384:     30 41 30 0D 06 09 60 86 48 01 65 03 04 02 02 05 00 04 30 ∥ H
SHA-512:     30 51 30 0D 06 09 60 86 48 01 65 03 04 02 03 05 00 04 40 ∥ H
SHA-512/224: 30 2D 30 0D 06 09 60 86 48 01 65 03 04 02 05 05 00 04 1C ∥ H
SHA-512/256: 30 31 30 0D 06 09 60 86 48 01 65 03 04 02 06 05 00 04 20 ∥ H

如果我們深入了解細則,這是一個DigestInfoValue。例如,最後一個條目解碼為

  • 30 31   49字節序列

    • 30 0D   13字節序列

      • 06 09   9 個字節的 OID

      • 05 00參數欄位   為NULL²

    • 04 20   32 字節的八位字節串

      • (散列H跟隨為 32 個字節)。

請參閱此處了解 OID 的編碼方式以及 ASN.1 DER 規範的連結。可以在 Lapo Luchini 的有用的ASN.1 解碼器中拋出範例。


¹ 給定一個簽名,可以創建一個新的公鑰/私鑰對,使該簽名與任何所需的雜湊標識符有效,並在使用此新公鑰檢查時匹配任何所需的已知消息(不僅是原始消息)。

² 編碼檢查時該欄位必須存在且為NULL $ T $ 在 RSASSA-PKCS1-v1_5 的上下文中。在其他情況下,解析器必須接受 SHA 算法缺少它,請參閱附錄 B.1中的異常和上面的兩段。

引用自:https://crypto.stackexchange.com/questions/80768