Skip to content

Commit 8dbf97b

Browse files
committed
rdar://161919434 Upstream pkg-signer* support
In order to make `pkg-signer*` work, we needed to make some changes to `swift-certificates` exposing certain entities publicly and adding trusted timestamp support to CMS.
1 parent ba4aeba commit 8dbf97b

2 files changed

Lines changed: 61 additions & 2 deletions

File tree

Sources/X509/CryptographicMessageSyntax/CMSSignerInfo.swift

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -137,7 +137,7 @@ struct CMSSignerInfo: DERImplicitlyTaggable, BERImplicitlyTaggable, Hashable, Se
137137
node in
138138
return try DER.set(
139139
of: CMSAttribute.self,
140-
identifier: .init(tagWithNumber: 0, tagClass: .contextSpecific),
140+
identifier: .init(tagWithNumber: 1, tagClass: .contextSpecific),
141141
rootNode: node
142142
)
143143
}
@@ -192,7 +192,7 @@ struct CMSSignerInfo: DERImplicitlyTaggable, BERImplicitlyTaggable, Hashable, Se
192192
node in
193193
return try BER.set(
194194
of: CMSAttribute.self,
195-
identifier: .init(tagWithNumber: 0, tagClass: .contextSpecific),
195+
identifier: .init(tagWithNumber: 1, tagClass: .contextSpecific),
196196
rootNode: node
197197
)
198198
}
Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,59 @@
1+
//===----------------------------------------------------------------------===//
2+
//
3+
// This source file is part of the SwiftCertificates open source project
4+
//
5+
// Copyright (c) 2026 Apple Inc. and the SwiftCertificates project authors
6+
// Licensed under Apache License v2.0
7+
//
8+
// See LICENSE.txt for license information
9+
// See CONTRIBUTORS.txt for the list of SwiftCertificates project authors
10+
//
11+
// SPDX-License-Identifier: Apache-2.0
12+
//
13+
//===----------------------------------------------------------------------===//
14+
15+
import XCTest
16+
import SwiftASN1
17+
@testable @_spi(CMS) import X509
18+
19+
final class CMSSignerInfoUnsignedAttributesRoundTripTest: XCTestCase
20+
{
21+
private func assertRoundTrips<ASN1Object: DERParseable & DERSerializable & Equatable>(_ value: ASN1Object)
22+
throws
23+
{
24+
var serializer = DER.Serializer()
25+
try serializer.serialize(value)
26+
let parsed = try ASN1Object(derEncoded: serializer.serializedBytes)
27+
XCTAssertEqual(parsed, value)
28+
}
29+
30+
func testCMSSignerInfoWithUnsignedAttrsRoundTrips()
31+
throws
32+
{
33+
// A SignerInfo carrying unsignedAttrs must survive a serialize/parse round trip.
34+
// This exercises the `[1] IMPLICIT` unsignedAttrs path.
35+
let unsignedAttr = CMSAttribute(
36+
attrType: .contentType,
37+
attrValues: [try ASN1Any(erasing: ASN1OctetString(contentBytes: [0xDE, 0xAD, 0xBE, 0xEF]))]
38+
)
39+
try assertRoundTrips(
40+
CMSSignerInfo(
41+
version: .v1,
42+
signerIdentifier: .issuerAndSerialNumber(
43+
.init(
44+
issuer: .init {
45+
CountryName("US")
46+
OrganizationName("Apple Inc.")
47+
CommonName("Apple Public EV Server ECC CA 1 - G1")
48+
},
49+
serialNumber: .init(bytes: [20, 30, 40, 50])
50+
)
51+
),
52+
digestAlgorithm: .sha256WithRSAEncryptionUsingNil,
53+
signatureAlgorithm: .ecdsaWithSHA256,
54+
signature: .init(contentBytes: [100, 110, 120, 130, 140]),
55+
unsignedAttrs: [unsignedAttr]
56+
)
57+
)
58+
}
59+
}

0 commit comments

Comments
 (0)