]> git.saurik.com Git - apple/security.git/blob - SecurityTests/clxutils/extractCertFields/extractCertFields.cpp
Security-57336.1.9.tar.gz
[apple/security.git] / SecurityTests / clxutils / extractCertFields / extractCertFields.cpp
1 /*
2 * Parse a cert, dump its subject name (in normalized DER-encoded form),
3 * key size, and public key blob to stdout.
4 */
5 #include <utilLib/common.h>
6 #include <utilLib/cspwrap.h>
7 #include <security_cdsa_utils/cuFileIo.h>
8 #include <security_cdsa_utils/cuPrintCert.h>
9 #include <clAppUtils/clutils.h>
10 #include <stdlib.h>
11 #include <stdio.h>
12 #include <string.h>
13 #include <Security/cssm.h>
14 #include <Security/oidscert.h>
15 #include <Security/SecAsn1Coder.h>
16 #include <Security/X509Templates.h>
17
18 #define WRITE_NAME_FILE 1
19
20 /* allow checking various DER encoded fields */
21 #define SUBJECT_NAME_OID CSSMOID_X509V1SubjectName /* normalized */
22 // #define SUBJECT_NAME_OID CSSMOID_X509V1SubjectNameStd /* non normalized */
23
24 /*
25 * Print the contents of a CSSM_DATA, like so:
26 *
27 * static const uint8 <label>_bytes[] = {
28 * ....contents.....
29 * };
30 * static const CSSM_DATA <label> = { length, (uint8 *)<label>_bytes} ;
31 */
32 static void dumpDataBlob(
33 const char *label,
34 const CSSM_DATA_PTR data)
35 {
36 unsigned i;
37
38 printf("static const uint8 %s_bytes[] = {\n ", label);
39 for(i=0; i<data->Length; i++) {
40 printf("0x%02x", data->Data[i]);
41 if(i != (data->Length - 1)) {
42 printf(", ");
43 }
44 if((i % 8) == 7) {
45 printf("\n ");
46 }
47 }
48 printf("\n};\n");
49 printf("static const CSSM_DATA %s = { %lu, (uint8 *)%s_bytes };\n",
50 label, data->Length, label);
51 }
52
53 static void printHeader(
54 const char *fileName,
55 CSSM_DATA_PTR subject)
56 {
57 CSSM_FIELD field;
58 OidParser parser(false); // quick parser, no config file
59
60 printf("/***********************\n");
61 printf("Cert File Name: %s\n", fileName);
62 field.FieldValue = *subject;
63 field.FieldOid = CSSMOID_X509V1SubjectNameCStruct;
64 printCertField(field, parser, true);
65 printf(" ***********************/\n");
66 }
67
68 int main(int argc, char **argv)
69 {
70 CSSM_CL_HANDLE clHand; // CL handle
71 CSSM_DATA rawCert = {0, NULL};
72 uint32 numFields;
73 CSSM_HANDLE ResultsHandle = 0;
74 char baseName[255];
75 char blobName[255];
76 char *cp;
77 int rtn;
78 int nameLen;
79 CSSM_RETURN crtn;
80 CSSM_DATA_PTR value;
81 CSSM_KEY_PTR key;
82 uint32 keySize;
83 NSS_Certificate signedCert;
84 SecAsn1CoderRef coder;
85
86 if(argc != 2) {
87 printf("usage: %s certFile\n", argv[0]);
88 exit(1);
89 }
90
91 /* connect to CL */
92 clHand = clStartup();
93 if(clHand == 0) {
94 printf("clStartup failure; aborting\n");
95 return 0;
96 }
97
98 /* subsequent errors to abort: */
99 /* read a in raw cert */
100 unsigned len;
101 rtn = readFile(argv[1], &rawCert.Data, &len);
102 if(rtn) {
103 printf("Error %s reading file %s\n", strerror(rtn), argv[1]);
104 exit(1);
105 }
106 rawCert.Length = len;
107
108 /* C string of file name, terminating at '.' or space */
109 nameLen = strlen(argv[1]);
110 memmove(baseName, argv[1], nameLen);
111 baseName[nameLen] = '\0';
112 cp = strchr(baseName, '.');
113 if(cp) {
114 *cp = '\0';
115 }
116 cp = strchr(baseName, ' ');
117 if(cp) {
118 *cp = '\0';
119 }
120
121 /* print filename and parsed subject name as comment */
122 crtn = CSSM_CL_CertGetFirstFieldValue(
123 clHand,
124 &rawCert,
125 &CSSMOID_X509V1SubjectNameCStruct,
126 &ResultsHandle,
127 &numFields,
128 &value);
129 if(crtn) {
130 printError("CSSM_CL_CertGetFirstFieldValue(CSSMOID_X509V1SubjectNameCStruct)", crtn);
131 goto abort;
132 }
133 CSSM_CL_CertAbortQuery(clHand, ResultsHandle);
134 if(value == NULL) {
135 printf("Error extracting subject name\n");
136 goto abort;
137 }
138 printHeader(argv[1], value);
139 CSSM_CL_FreeFieldValue(clHand, &CSSMOID_X509V1SubjectNameCStruct, value);
140
141 /* print normalized & encoded subject name as C data */
142 crtn = CSSM_CL_CertGetFirstFieldValue(
143 clHand,
144 &rawCert,
145 &SUBJECT_NAME_OID,
146 &ResultsHandle,
147 &numFields,
148 &value);
149 if(crtn) {
150 printError("CSSM_CL_CertGetFirstFieldValue(CSSMOID_X509V1SubjectName)", crtn);
151 goto abort;
152 }
153 CSSM_CL_CertAbortQuery(clHand, ResultsHandle);
154 if(value == NULL) {
155 printf("Error extracting subject name\n");
156 goto abort;
157 }
158 sprintf(blobName, "%s_subject", baseName);
159 dumpDataBlob(blobName, value);
160 #if WRITE_NAME_FILE
161 writeFile(blobName, value->Data, (unsigned)value->Length);
162 #endif
163 CSSM_CL_FreeFieldValue(clHand, &SUBJECT_NAME_OID, value);
164
165 /* print key blob as data */
166 crtn = CSSM_CL_CertGetFirstFieldValue(
167 clHand,
168 &rawCert,
169 &CSSMOID_CSSMKeyStruct,
170 &ResultsHandle,
171 &numFields,
172 &value);
173 if(crtn) {
174 printError("CSSM_CL_CertGetFirstFieldValue(CSSMOID_CSSMKeyStruct)", crtn);
175 goto abort;
176 }
177 CSSM_CL_CertAbortQuery(clHand, ResultsHandle );
178 if(value == NULL) {
179 printf("Error extracting public key\n");
180 goto abort;
181 }
182 if(value->Length != sizeof(CSSM_KEY)) {
183 printf("CSSMOID_CSSMKeyStruct length error\n");
184 goto abort;
185 }
186 key = (CSSM_KEY_PTR)value->Data;
187 sprintf(blobName, "%s_pubKey", baseName);
188 dumpDataBlob(blobName, &key->KeyData);
189 keySize = key->KeyHeader.LogicalKeySizeInBits;
190 CSSM_CL_FreeFieldValue(clHand, &CSSMOID_CSSMKeyStruct, value);
191
192 /* unnormalized DER-encoded issuer */
193 SecAsn1CoderCreate(&coder);
194 memset(&signedCert, 0, sizeof(signedCert));
195 if(SecAsn1DecodeData(coder, &rawCert, kSecAsn1SignedCertTemplate, &signedCert)) {
196 printf("***Error NSS-decoding certificate\n");
197 }
198 else {
199 sprintf(blobName, "%s_derIssuer", baseName);
200 dumpDataBlob(blobName, &signedCert.tbs.derIssuer);
201 }
202 /* now the the struct containing all three */
203 printf("\n { &%s_subject, &%s_pubKey, %u },\n", baseName, baseName, (unsigned)keySize);
204 abort:
205 free(rawCert.Data);
206 if(clHand != 0) {
207 CSSM_ModuleDetach(clHand);
208 }
209 SecAsn1CoderRelease(coder);
210 return 0;
211 }