1/* 2 * Copyright (c) 2012-2014 Apple Inc. All Rights Reserved. 3 * 4 * @APPLE_LICENSE_HEADER_START@ 5 * 6 * This file contains Original Code and/or Modifications of Original Code 7 * as defined in and that are subject to the Apple Public Source License 8 * Version 2.0 (the 'License'). You may not use this file except in 9 * compliance with the License. Please obtain a copy of the License at 10 * http://www.opensource.apple.com/apsl/ and read it before using this 11 * file. 12 * 13 * The Original Code and all software distributed under the License are 14 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER 15 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES, 16 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY, 17 * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT. 18 * Please see the License for the specific language governing rights and 19 * limitations under the License. 20 * 21 * @APPLE_LICENSE_HEADER_END@ 22 * 23 * tsaTemplates.c - ASN1 templates Time Stamping Authority requests and responses 24 */ 25 26#include <security_asn1/keyTemplates.h> /* for kSecAsn1AlgorithmIDTemplate */ 27#include <security_asn1/SecAsn1Templates.h> 28#include <stddef.h> 29#include <assert.h> 30 31#include "tsaTemplates.h" 32#include "cmslocal.h" 33 34#pragma clang diagnostic push 35#pragma clang diagnostic ignored "-Wunused-const-variable" 36 37// *** from CMSEncoder.cpp 38 39typedef struct { 40 CSSM_OID contentType; 41 CSSM_DATA content; 42} SimpleContentInfo; 43 44// SecCmsContentInfoTemplate 45static const SecAsn1Template cmsSimpleContentInfoTemplate[] = { 46 { SEC_ASN1_SEQUENCE, 0, NULL, sizeof(SimpleContentInfo) }, 47 { SEC_ASN1_OBJECT_ID, offsetof(SimpleContentInfo, contentType) }, 48 { SEC_ASN1_EXPLICIT | SEC_ASN1_CONSTRUCTED | SEC_ASN1_CONTEXT_SPECIFIC | 0, 49 offsetof(SimpleContentInfo, content), 50 kSecAsn1AnyTemplate }, 51 { 0, } 52}; 53 54#pragma mark ----- tsa ----- 55 56/* 57Accuracy ::= SEQUENCE { 58 seconds INTEGER OPTIONAL, 59 millis [0] INTEGER (1..999) OPTIONAL, 60 micros [1] INTEGER (1..999) OPTIONAL } 61*/ 62 63const SecAsn1Template kSecAsn1SignedIntegerTemplate[] = { 64 { SEC_ASN1_INTEGER | SEC_ASN1_SIGNED_INT, 0, NULL, sizeof(SecAsn1Item) } 65}; 66 67const SecAsn1Template kSecAsn1UnsignedIntegerTemplate[] = { 68 { SEC_ASN1_INTEGER, 0, NULL, sizeof(SecAsn1Item) } 69}; 70 71const SecAsn1Template kSecAsn1TSAAccuracyTemplate[] = { 72 { SEC_ASN1_SEQUENCE, 73 0, NULL, sizeof(SecAsn1TSAAccuracy) }, 74 { SEC_ASN1_INTEGER, 75 offsetof(SecAsn1TSAAccuracy, seconds) }, 76 { SEC_ASN1_CONTEXT_SPECIFIC | 0 | SEC_ASN1_OPTIONAL, 77 offsetof(SecAsn1TSAAccuracy, millis), kSecAsn1UnsignedIntegerTemplate }, 78 { SEC_ASN1_CONTEXT_SPECIFIC | 1 | SEC_ASN1_OPTIONAL, 79 offsetof(SecAsn1TSAAccuracy, micros), kSecAsn1UnsignedIntegerTemplate }, 80 { 0 } 81}; 82 83/* 84MessageImprint ::= SEQUENCE { 85 hashAlgorithm AlgorithmIdentifier, 86 hashedMessage OCTET STRING } 87*/ 88 89const SecAsn1Template kSecAsn1TSAMessageImprintTemplate[] = { 90 { SEC_ASN1_SEQUENCE, 91 0, NULL, sizeof(SecAsn1TSAMessageImprint) }, 92 { SEC_ASN1_INLINE, offsetof(SecAsn1TSAMessageImprint,hashAlgorithm), 93 kSecAsn1AlgorithmIDTemplate }, 94 { SEC_ASN1_OCTET_STRING, 95 offsetof(SecAsn1TSAMessageImprint,hashedMessage) }, 96 { 0 } 97}; 98 99/* 100 TimeStampReq ::= SEQUENCE { 101 version INTEGER { v1(1) }, 102 messageImprint MessageImprint, 103 --a hash algorithm OID and the hash value of the data to be 104 --time-stamped 105 reqPolicy TSAPolicyId OPTIONAL, 106 nonce INTEGER OPTIONAL, 107 certReq BOOLEAN DEFAULT FALSE, 108 extensions [0] IMPLICIT Extensions OPTIONAL } 109 110 MessageImprint ::= SEQUENCE { 111 hashAlgorithm AlgorithmIdentifier, 112 hashedMessage OCTET STRING } 113 114 TSAPolicyId ::= OBJECT IDENTIFIER 115*/ 116 117const SecAsn1Template kSecAsn1TSATimeStampReqTemplate[] = { 118 { SEC_ASN1_SEQUENCE, 119 0, NULL, sizeof(SecAsn1TSATimeStampReq) }, 120 { SEC_ASN1_INTEGER, 121 offsetof(SecAsn1TSATimeStampReq, version) }, 122 { SEC_ASN1_INLINE, offsetof(SecAsn1TSATimeStampReq,messageImprint), 123 kSecAsn1TSAMessageImprintTemplate }, 124 { SEC_ASN1_OBJECT_ID | SEC_ASN1_OPTIONAL, 125 offsetof(SecAsn1TSATimeStampReq,reqPolicy) }, 126 { SEC_ASN1_INTEGER | SEC_ASN1_OPTIONAL, 127 offsetof(SecAsn1TSATimeStampReq, nonce) }, 128 { SEC_ASN1_BOOLEAN | SEC_ASN1_OPTIONAL, 129 offsetof(SecAsn1TSATimeStampReq, certReq) }, 130 { SEC_ASN1_OPTIONAL | SEC_ASN1_CONSTRUCTED | SEC_ASN1_CONTEXT_SPECIFIC | 0, 131 offsetof(SecAsn1TSATimeStampReq, extensions), 132 kSecAsn1SequenceOfCertExtensionTemplate }, 133 { 0 } 134}; 135 136/* 137 PKIFreeText ::= SEQUENCE { 138 SIZE (1..MAX) OF UTF8String 139 -- text encoded as UTF-8 String (note: each UTF8String SHOULD 140 -- include an RFC 1766 language tag to indicate the language -- of the contained text) 141 } 142 143 See e.g. kSecAsn1SequenceOfUTF8StringTemplate 144*/ 145 146const SecAsn1Template kSecAsn1TSAPKIStatusInfoTemplate[] = { 147 { SEC_ASN1_SEQUENCE, 148 0, NULL, sizeof(SecAsn1TSAPKIStatusInfo) }, 149 { SEC_ASN1_INTEGER, 150 offsetof(SecAsn1TSAPKIStatusInfo, status) }, 151 { SEC_ASN1_CONSTRUCTED | SEC_ASN1_SEQUENCE | SEC_ASN1_OPTIONAL, 152 offsetof(SecAsn1TSAPKIStatusInfo, statusString) }, 153 { SEC_ASN1_BIT_STRING | SEC_ASN1_OPTIONAL, 154 offsetof(SecAsn1TSAPKIStatusInfo,failInfo) }, 155 { 0 } 156}; 157 158const SecAsn1Template kSecAsn1TSAPKIStatusInfoTemplateRFC3161[] = { 159 { SEC_ASN1_SEQUENCE, 160 0, NULL, sizeof(SecAsn1TSAPKIStatusInfo) }, 161 { SEC_ASN1_INTEGER, 162 offsetof(SecAsn1TSAPKIStatusInfo, status) }, 163 { SEC_ASN1_UTF8_STRING | SEC_ASN1_OPTIONAL, 164 offsetof(SecAsn1TSAPKIStatusInfo, statusString) }, 165 { SEC_ASN1_BIT_STRING | SEC_ASN1_OPTIONAL, 166 offsetof(SecAsn1TSAPKIStatusInfo,failInfo) }, 167 { 0 } 168}; 169 170const SecAsn1Template kSecAsn1TSATimeStampRespTemplate[] = { 171 { SEC_ASN1_SEQUENCE, 172 0, NULL, sizeof(SecAsn1TimeStampResp) }, 173 { SEC_ASN1_INLINE, offsetof(SecAsn1TimeStampResp,status), 174 kSecAsn1TSAPKIStatusInfoTemplate }, 175 { SEC_ASN1_INLINE | SEC_ASN1_OPTIONAL, offsetof(SecAsn1TimeStampResp,timeStampToken), 176 SecCmsContentInfoTemplate }, 177 { 0 } 178}; 179 180// Decode the status but not the TimeStampToken 181const SecAsn1Template kSecAsn1TSATimeStampRespTemplateDER[] = { 182 { SEC_ASN1_SEQUENCE, 183 0, NULL, sizeof(SecAsn1TimeStampRespDER) }, 184 { SEC_ASN1_INLINE, offsetof(SecAsn1TimeStampRespDER,status), 185 kSecAsn1TSAPKIStatusInfoTemplate }, 186 { SEC_ASN1_ANY | SEC_ASN1_OPTIONAL ,//| SEC_ASN1_SAVE, 187 offsetof(SecAsn1TimeStampRespDER, timeStampTokenDER), kSecAsn1AnyTemplate }, 188 { 0 } 189}; 190 191/* 192 RFC 3161 Time-Stamp Protocol (TSP) August 2001 193 194 TimeStampToken ::= ContentInfo 195 196 -- contentType is id-signedData as defined in [CMS] 197 -- content is SignedData as defined in([CMS]) 198 -- eContentType within SignedData is id-ct-TSTInfo 199 -- eContent within SignedData is TSTInfo 200 201 TSTInfo ::= SEQUENCE { 202 version INTEGER { v1(1) }, 203 policy TSAPolicyId, 204 messageImprint MessageImprint, 205 -- MUST have the same value as the similar field in 206 -- TimeStampReq 207 serialNumber INTEGER, 208 -- Time-Stamping users MUST be ready to accommodate integers 209 -- up to 160 bits. 210 genTime GeneralizedTime, 211 accuracy Accuracy OPTIONAL, 212 ordering BOOLEAN DEFAULT FALSE, 213 nonce INTEGER OPTIONAL, 214 -- MUST be present if the similar field was present 215 -- in TimeStampReq. In that case it MUST have the same value. 216 tsa [0] GeneralName OPTIONAL, 217 extensions [1] IMPLICIT Extensions OPTIONAL } 218 219 Accuracy ::= SEQUENCE { 220 seconds INTEGER OPTIONAL, 221 millis [0] INTEGER (1..999) OPTIONAL, 222 micros [1] INTEGER (1..999) OPTIONAL } 223*/ 224 225const SecAsn1Template kSecAsn1TSATSTInfoTemplate[] = { 226 { SEC_ASN1_SEQUENCE, 227 0, NULL, sizeof(SecAsn1TSATSTInfo) }, 228 { SEC_ASN1_INTEGER, 229 offsetof(SecAsn1TSATSTInfo, version) }, 230 { SEC_ASN1_OBJECT_ID, 231 offsetof(SecAsn1TSATSTInfo,reqPolicy) }, 232 { SEC_ASN1_INLINE, offsetof(SecAsn1TSATSTInfo,messageImprint), 233 kSecAsn1TSAMessageImprintTemplate }, 234 { SEC_ASN1_INTEGER, 235 offsetof(SecAsn1TSATSTInfo, serialNumber) }, 236 { SEC_ASN1_GENERALIZED_TIME | SEC_ASN1_MAY_STREAM, 237 offsetof(SecAsn1TSATSTInfo,genTime) }, 238 { SEC_ASN1_INLINE | SEC_ASN1_OPTIONAL, 239 offsetof(SecAsn1TSATSTInfo,accuracy), 240 kSecAsn1TSAAccuracyTemplate }, 241 { SEC_ASN1_BOOLEAN | SEC_ASN1_OPTIONAL, 242 offsetof(SecAsn1TSATSTInfo, ordering) }, 243 { SEC_ASN1_INTEGER | SEC_ASN1_OPTIONAL, 244 offsetof(SecAsn1TSATSTInfo, nonce) }, 245 { SEC_ASN1_CONSTRUCTED | SEC_ASN1_CONTEXT_SPECIFIC | 0 | SEC_ASN1_OPTIONAL, 246 offsetof(SecAsn1TSATSTInfo, tsa), 247 kSecAsn1GenNameOtherNameTemplate}, 248 249 { SEC_ASN1_CONSTRUCTED | SEC_ASN1_CONTEXT_SPECIFIC | 1 | SEC_ASN1_OPTIONAL, 250 offsetof(SecAsn1TSATSTInfo, extensions), 251 kSecAsn1CertExtensionTemplate }, 252 { 0 } 253}; 254 255#pragma clang diagnostic pop 256