diff options
Diffstat (limited to 'src/lib/libcrypto/pkcs7/example.c')
-rw-r--r-- | src/lib/libcrypto/pkcs7/example.c | 329 |
1 files changed, 329 insertions, 0 deletions
diff --git a/src/lib/libcrypto/pkcs7/example.c b/src/lib/libcrypto/pkcs7/example.c new file mode 100644 index 0000000000..c993947cc3 --- /dev/null +++ b/src/lib/libcrypto/pkcs7/example.c | |||
@@ -0,0 +1,329 @@ | |||
1 | #include <stdio.h> | ||
2 | #include <stdlib.h> | ||
3 | #include <string.h> | ||
4 | #include <openssl/pkcs7.h> | ||
5 | #include <openssl/asn1_mac.h> | ||
6 | #include <openssl/x509.h> | ||
7 | |||
8 | int add_signed_time(PKCS7_SIGNER_INFO *si) | ||
9 | { | ||
10 | ASN1_UTCTIME *sign_time; | ||
11 | |||
12 | /* The last parameter is the amount to add/subtract from the current | ||
13 | * time (in seconds) */ | ||
14 | sign_time=X509_gmtime_adj(NULL,0); | ||
15 | PKCS7_add_signed_attribute(si,NID_pkcs9_signingTime, | ||
16 | V_ASN1_UTCTIME,(char *)sign_time); | ||
17 | return(1); | ||
18 | } | ||
19 | |||
20 | ASN1_UTCTIME *get_signed_time(PKCS7_SIGNER_INFO *si) | ||
21 | { | ||
22 | ASN1_TYPE *so; | ||
23 | |||
24 | so=PKCS7_get_signed_attribute(si,NID_pkcs9_signingTime); | ||
25 | if (so->type == V_ASN1_UTCTIME) | ||
26 | return so->value.utctime; | ||
27 | return NULL; | ||
28 | } | ||
29 | |||
30 | static int signed_string_nid= -1; | ||
31 | |||
32 | void add_signed_string(PKCS7_SIGNER_INFO *si, char *str) | ||
33 | { | ||
34 | ASN1_OCTET_STRING *os; | ||
35 | |||
36 | /* To a an object of OID 1.2.3.4.5, which is an octet string */ | ||
37 | if (signed_string_nid == -1) | ||
38 | signed_string_nid= | ||
39 | OBJ_create("1.2.3.4.5","OID_example","Our example OID"); | ||
40 | os=ASN1_OCTET_STRING_new(); | ||
41 | ASN1_OCTET_STRING_set(os,(unsigned char*)str,strlen(str)); | ||
42 | /* When we add, we do not free */ | ||
43 | PKCS7_add_signed_attribute(si,signed_string_nid, | ||
44 | V_ASN1_OCTET_STRING,(char *)os); | ||
45 | } | ||
46 | |||
47 | int get_signed_string(PKCS7_SIGNER_INFO *si, char *buf, int len) | ||
48 | { | ||
49 | ASN1_TYPE *so; | ||
50 | ASN1_OCTET_STRING *os; | ||
51 | int i; | ||
52 | |||
53 | if (signed_string_nid == -1) | ||
54 | signed_string_nid= | ||
55 | OBJ_create("1.2.3.4.5","OID_example","Our example OID"); | ||
56 | /* To retrieve */ | ||
57 | so=PKCS7_get_signed_attribute(si,signed_string_nid); | ||
58 | if (so != NULL) | ||
59 | { | ||
60 | if (so->type == V_ASN1_OCTET_STRING) | ||
61 | { | ||
62 | os=so->value.octet_string; | ||
63 | i=os->length; | ||
64 | if ((i+1) > len) | ||
65 | i=len-1; | ||
66 | memcpy(buf,os->data,i); | ||
67 | return(i); | ||
68 | } | ||
69 | } | ||
70 | return(0); | ||
71 | } | ||
72 | |||
73 | static int signed_seq2string_nid= -1; | ||
74 | /* ########################################### */ | ||
75 | int add_signed_seq2string(PKCS7_SIGNER_INFO *si, char *str1, char *str2) | ||
76 | { | ||
77 | /* To add an object of OID 1.9.999, which is a sequence containing | ||
78 | * 2 octet strings */ | ||
79 | unsigned char *p; | ||
80 | ASN1_OCTET_STRING *os1,*os2; | ||
81 | ASN1_STRING *seq; | ||
82 | unsigned char *data; | ||
83 | int i,total; | ||
84 | |||
85 | if (signed_seq2string_nid == -1) | ||
86 | signed_seq2string_nid= | ||
87 | OBJ_create("1.9.9999","OID_example","Our example OID"); | ||
88 | |||
89 | os1=ASN1_OCTET_STRING_new(); | ||
90 | os2=ASN1_OCTET_STRING_new(); | ||
91 | ASN1_OCTET_STRING_set(os1,(unsigned char*)str1,strlen(str1)); | ||
92 | ASN1_OCTET_STRING_set(os2,(unsigned char*)str1,strlen(str1)); | ||
93 | i =i2d_ASN1_OCTET_STRING(os1,NULL); | ||
94 | i+=i2d_ASN1_OCTET_STRING(os2,NULL); | ||
95 | total=ASN1_object_size(1,i,V_ASN1_SEQUENCE); | ||
96 | |||
97 | data=malloc(total); | ||
98 | p=data; | ||
99 | ASN1_put_object(&p,1,i,V_ASN1_SEQUENCE,V_ASN1_UNIVERSAL); | ||
100 | i2d_ASN1_OCTET_STRING(os1,&p); | ||
101 | i2d_ASN1_OCTET_STRING(os2,&p); | ||
102 | |||
103 | seq=ASN1_STRING_new(); | ||
104 | ASN1_STRING_set(seq,data,total); | ||
105 | free(data); | ||
106 | ASN1_OCTET_STRING_free(os1); | ||
107 | ASN1_OCTET_STRING_free(os2); | ||
108 | |||
109 | PKCS7_add_signed_attribute(si,signed_seq2string_nid, | ||
110 | V_ASN1_SEQUENCE,(char *)seq); | ||
111 | return(1); | ||
112 | } | ||
113 | |||
114 | /* For this case, I will malloc the return strings */ | ||
115 | int get_signed_seq2string(PKCS7_SIGNER_INFO *si, char **str1, char **str2) | ||
116 | { | ||
117 | ASN1_TYPE *so; | ||
118 | |||
119 | if (signed_seq2string_nid == -1) | ||
120 | signed_seq2string_nid= | ||
121 | OBJ_create("1.9.9999","OID_example","Our example OID"); | ||
122 | /* To retrieve */ | ||
123 | so=PKCS7_get_signed_attribute(si,signed_seq2string_nid); | ||
124 | if (so && (so->type == V_ASN1_SEQUENCE)) | ||
125 | { | ||
126 | ASN1_CTX c; | ||
127 | ASN1_STRING *s; | ||
128 | long length; | ||
129 | ASN1_OCTET_STRING *os1,*os2; | ||
130 | |||
131 | s=so->value.sequence; | ||
132 | c.p=ASN1_STRING_data(s); | ||
133 | c.max=c.p+ASN1_STRING_length(s); | ||
134 | if (!asn1_GetSequence(&c,&length)) goto err; | ||
135 | /* Length is the length of the seqence */ | ||
136 | |||
137 | c.q=c.p; | ||
138 | if ((os1=d2i_ASN1_OCTET_STRING(NULL,&c.p,c.slen)) == NULL) | ||
139 | goto err; | ||
140 | c.slen-=(c.p-c.q); | ||
141 | |||
142 | c.q=c.p; | ||
143 | if ((os2=d2i_ASN1_OCTET_STRING(NULL,&c.p,c.slen)) == NULL) | ||
144 | goto err; | ||
145 | c.slen-=(c.p-c.q); | ||
146 | |||
147 | if (!asn1_Finish(&c)) goto err; | ||
148 | *str1=malloc(os1->length+1); | ||
149 | *str2=malloc(os2->length+1); | ||
150 | memcpy(*str1,os1->data,os1->length); | ||
151 | memcpy(*str2,os2->data,os2->length); | ||
152 | (*str1)[os1->length]='\0'; | ||
153 | (*str2)[os2->length]='\0'; | ||
154 | ASN1_OCTET_STRING_free(os1); | ||
155 | ASN1_OCTET_STRING_free(os2); | ||
156 | return(1); | ||
157 | } | ||
158 | err: | ||
159 | return(0); | ||
160 | } | ||
161 | |||
162 | |||
163 | /* ####################################### | ||
164 | * THE OTHER WAY TO DO THINGS | ||
165 | * ####################################### | ||
166 | */ | ||
167 | X509_ATTRIBUTE *create_time(void) | ||
168 | { | ||
169 | ASN1_UTCTIME *sign_time; | ||
170 | X509_ATTRIBUTE *ret; | ||
171 | |||
172 | /* The last parameter is the amount to add/subtract from the current | ||
173 | * time (in seconds) */ | ||
174 | sign_time=X509_gmtime_adj(NULL,0); | ||
175 | ret=X509_ATTRIBUTE_create(NID_pkcs9_signingTime, | ||
176 | V_ASN1_UTCTIME,(char *)sign_time); | ||
177 | return(ret); | ||
178 | } | ||
179 | |||
180 | ASN1_UTCTIME *sk_get_time(STACK_OF(X509_ATTRIBUTE) *sk) | ||
181 | { | ||
182 | ASN1_TYPE *so; | ||
183 | PKCS7_SIGNER_INFO si; | ||
184 | |||
185 | si.auth_attr=sk; | ||
186 | so=PKCS7_get_signed_attribute(&si,NID_pkcs9_signingTime); | ||
187 | if (so->type == V_ASN1_UTCTIME) | ||
188 | return so->value.utctime; | ||
189 | return NULL; | ||
190 | } | ||
191 | |||
192 | X509_ATTRIBUTE *create_string(char *str) | ||
193 | { | ||
194 | ASN1_OCTET_STRING *os; | ||
195 | X509_ATTRIBUTE *ret; | ||
196 | |||
197 | /* To a an object of OID 1.2.3.4.5, which is an octet string */ | ||
198 | if (signed_string_nid == -1) | ||
199 | signed_string_nid= | ||
200 | OBJ_create("1.2.3.4.5","OID_example","Our example OID"); | ||
201 | os=ASN1_OCTET_STRING_new(); | ||
202 | ASN1_OCTET_STRING_set(os,(unsigned char*)str,strlen(str)); | ||
203 | /* When we add, we do not free */ | ||
204 | ret=X509_ATTRIBUTE_create(signed_string_nid, | ||
205 | V_ASN1_OCTET_STRING,(char *)os); | ||
206 | return(ret); | ||
207 | } | ||
208 | |||
209 | int sk_get_string(STACK_OF(X509_ATTRIBUTE) *sk, char *buf, int len) | ||
210 | { | ||
211 | ASN1_TYPE *so; | ||
212 | ASN1_OCTET_STRING *os; | ||
213 | int i; | ||
214 | PKCS7_SIGNER_INFO si; | ||
215 | |||
216 | si.auth_attr=sk; | ||
217 | |||
218 | if (signed_string_nid == -1) | ||
219 | signed_string_nid= | ||
220 | OBJ_create("1.2.3.4.5","OID_example","Our example OID"); | ||
221 | /* To retrieve */ | ||
222 | so=PKCS7_get_signed_attribute(&si,signed_string_nid); | ||
223 | if (so != NULL) | ||
224 | { | ||
225 | if (so->type == V_ASN1_OCTET_STRING) | ||
226 | { | ||
227 | os=so->value.octet_string; | ||
228 | i=os->length; | ||
229 | if ((i+1) > len) | ||
230 | i=len-1; | ||
231 | memcpy(buf,os->data,i); | ||
232 | return(i); | ||
233 | } | ||
234 | } | ||
235 | return(0); | ||
236 | } | ||
237 | |||
238 | X509_ATTRIBUTE *add_seq2string(PKCS7_SIGNER_INFO *si, char *str1, char *str2) | ||
239 | { | ||
240 | /* To add an object of OID 1.9.999, which is a sequence containing | ||
241 | * 2 octet strings */ | ||
242 | unsigned char *p; | ||
243 | ASN1_OCTET_STRING *os1,*os2; | ||
244 | ASN1_STRING *seq; | ||
245 | X509_ATTRIBUTE *ret; | ||
246 | unsigned char *data; | ||
247 | int i,total; | ||
248 | |||
249 | if (signed_seq2string_nid == -1) | ||
250 | signed_seq2string_nid= | ||
251 | OBJ_create("1.9.9999","OID_example","Our example OID"); | ||
252 | |||
253 | os1=ASN1_OCTET_STRING_new(); | ||
254 | os2=ASN1_OCTET_STRING_new(); | ||
255 | ASN1_OCTET_STRING_set(os1,(unsigned char*)str1,strlen(str1)); | ||
256 | ASN1_OCTET_STRING_set(os2,(unsigned char*)str1,strlen(str1)); | ||
257 | i =i2d_ASN1_OCTET_STRING(os1,NULL); | ||
258 | i+=i2d_ASN1_OCTET_STRING(os2,NULL); | ||
259 | total=ASN1_object_size(1,i,V_ASN1_SEQUENCE); | ||
260 | |||
261 | data=malloc(total); | ||
262 | p=data; | ||
263 | ASN1_put_object(&p,1,i,V_ASN1_SEQUENCE,V_ASN1_UNIVERSAL); | ||
264 | i2d_ASN1_OCTET_STRING(os1,&p); | ||
265 | i2d_ASN1_OCTET_STRING(os2,&p); | ||
266 | |||
267 | seq=ASN1_STRING_new(); | ||
268 | ASN1_STRING_set(seq,data,total); | ||
269 | free(data); | ||
270 | ASN1_OCTET_STRING_free(os1); | ||
271 | ASN1_OCTET_STRING_free(os2); | ||
272 | |||
273 | ret=X509_ATTRIBUTE_create(signed_seq2string_nid, | ||
274 | V_ASN1_SEQUENCE,(char *)seq); | ||
275 | return(ret); | ||
276 | } | ||
277 | |||
278 | /* For this case, I will malloc the return strings */ | ||
279 | int sk_get_seq2string(STACK_OF(X509_ATTRIBUTE) *sk, char **str1, char **str2) | ||
280 | { | ||
281 | ASN1_TYPE *so; | ||
282 | PKCS7_SIGNER_INFO si; | ||
283 | |||
284 | if (signed_seq2string_nid == -1) | ||
285 | signed_seq2string_nid= | ||
286 | OBJ_create("1.9.9999","OID_example","Our example OID"); | ||
287 | |||
288 | si.auth_attr=sk; | ||
289 | /* To retrieve */ | ||
290 | so=PKCS7_get_signed_attribute(&si,signed_seq2string_nid); | ||
291 | if (so->type == V_ASN1_SEQUENCE) | ||
292 | { | ||
293 | ASN1_CTX c; | ||
294 | ASN1_STRING *s; | ||
295 | long length; | ||
296 | ASN1_OCTET_STRING *os1,*os2; | ||
297 | |||
298 | s=so->value.sequence; | ||
299 | c.p=ASN1_STRING_data(s); | ||
300 | c.max=c.p+ASN1_STRING_length(s); | ||
301 | if (!asn1_GetSequence(&c,&length)) goto err; | ||
302 | /* Length is the length of the seqence */ | ||
303 | |||
304 | c.q=c.p; | ||
305 | if ((os1=d2i_ASN1_OCTET_STRING(NULL,&c.p,c.slen)) == NULL) | ||
306 | goto err; | ||
307 | c.slen-=(c.p-c.q); | ||
308 | |||
309 | c.q=c.p; | ||
310 | if ((os2=d2i_ASN1_OCTET_STRING(NULL,&c.p,c.slen)) == NULL) | ||
311 | goto err; | ||
312 | c.slen-=(c.p-c.q); | ||
313 | |||
314 | if (!asn1_Finish(&c)) goto err; | ||
315 | *str1=malloc(os1->length+1); | ||
316 | *str2=malloc(os2->length+1); | ||
317 | memcpy(*str1,os1->data,os1->length); | ||
318 | memcpy(*str2,os2->data,os2->length); | ||
319 | (*str1)[os1->length]='\0'; | ||
320 | (*str2)[os2->length]='\0'; | ||
321 | ASN1_OCTET_STRING_free(os1); | ||
322 | ASN1_OCTET_STRING_free(os2); | ||
323 | return(1); | ||
324 | } | ||
325 | err: | ||
326 | return(0); | ||
327 | } | ||
328 | |||
329 | |||