From 2e32e679d0d3c30d027696e5aa74121720a2a2fa Mon Sep 17 00:00:00 2001 From: Vault Automation Date: Tue, 27 Jan 2026 12:07:07 -0500 Subject: [PATCH] Backport PKI (SCEP): support compound octet strings for inner PKCS7 content into ce/main (#12021) * PKI (SCEP): support compound octet strings for inner PKCS7 content (#12019) * Support compound octet strings for inner PKCS7 content * Add cl * Remove hashicorp/go-cmp ENT dependency --------- Co-authored-by: Steven Clark --- changelog/_12019.txt | 3 +++ helper/pkcs7/verify.go | 9 +++++++-- helper/pkcs7/verify_test.go | 29 +++++++++++++++++++++++++++++ 3 files changed, 39 insertions(+), 2 deletions(-) create mode 100644 changelog/_12019.txt create mode 100644 helper/pkcs7/verify_test.go diff --git a/changelog/_12019.txt b/changelog/_12019.txt new file mode 100644 index 0000000000..f45545ac45 --- /dev/null +++ b/changelog/_12019.txt @@ -0,0 +1,3 @@ +```release-note:bug +secrets/pki (enterprise): Fix SCEP related digest errors when requests contained compound octet strings +``` diff --git a/helper/pkcs7/verify.go b/helper/pkcs7/verify.go index cdc62246d2..ea93136ec2 100644 --- a/helper/pkcs7/verify.go +++ b/helper/pkcs7/verify.go @@ -268,8 +268,13 @@ func parseSignedData(data []byte) (*PKCS7, error) { // Compound octet string if compound.IsCompound { if compound.Tag == 4 { - if _, err = asn1.Unmarshal(compound.Bytes, &content); err != nil { - return nil, err + for len(compound.Bytes) > 0 { + var cdata asn1.RawValue + if _, err = asn1.Unmarshal(compound.Bytes, &cdata); err != nil { + return nil, err + } + content = append(content, cdata.Bytes...) + compound.Bytes = compound.Bytes[len(cdata.FullBytes):] } } else { content = compound.Bytes diff --git a/helper/pkcs7/verify_test.go b/helper/pkcs7/verify_test.go new file mode 100644 index 0000000000..e29b9008fc --- /dev/null +++ b/helper/pkcs7/verify_test.go @@ -0,0 +1,29 @@ +package pkcs7 + +import ( + "encoding/base64" + "testing" + + "github.com/stretchr/testify/require" +) + +// TestSCEPMsgWithCompoundOctetString tests parsing and verifying a PKCS7 SCEP message +// where the content is a compound octet string (i.e. multiple octet strings concatenated together). +// BouncyCastle, the library that jSCEP uses, produces such messages. +func TestSCEPMsgWithCompoundOctetString(t *testing.T) { + fullMsgB64 := "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" + fullMsg, err := base64.StdEncoding.DecodeString(fullMsgB64) + require.NoError(t, err, "failed decoding base64 fullMsg") + + myPkcs7Msg, err := Parse(fullMsg) + require.NoError(t, err, "failed parsing fullMsg") + // The content is a compound octet string, so ensure we read all parts + // if we only read the first part, the length would be 1000 + require.Equal(t, 1187, len(myPkcs7Msg.Content), "The length of the content was short read") + + err = myPkcs7Msg.Verify() + require.NoError(t, err, "failed verifying pkcs7 message") + + _, err = Parse(myPkcs7Msg.Content) + require.NoError(t, err, "failed parsing inner cert pkcs7") +}