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