1656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project#include <stdio.h>
2656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project#include <stdlib.h>
3656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project#include <string.h>
4656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project#include <openssl/pkcs7.h>
5656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project#include <openssl/asn1_mac.h>
6656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project#include <openssl/x509.h>
7656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
8656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Projectint add_signed_time(PKCS7_SIGNER_INFO *si)
9656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	{
10656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_UTCTIME *sign_time;
11656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
12656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	/* The last parameter is the amount to add/subtract from the current
13656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	 * time (in seconds) */
14656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	sign_time=X509_gmtime_adj(NULL,0);
15656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	PKCS7_add_signed_attribute(si,NID_pkcs9_signingTime,
16656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		V_ASN1_UTCTIME,(char *)sign_time);
17656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	return(1);
18656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	}
19656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
20656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source ProjectASN1_UTCTIME *get_signed_time(PKCS7_SIGNER_INFO *si)
21656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	{
22656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_TYPE *so;
23656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
24656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	so=PKCS7_get_signed_attribute(si,NID_pkcs9_signingTime);
25656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	if (so->type == V_ASN1_UTCTIME)
26656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	    return so->value.utctime;
27656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	return NULL;
28656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	}
29656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
30656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Projectstatic int signed_string_nid= -1;
31656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
32656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Projectvoid add_signed_string(PKCS7_SIGNER_INFO *si, char *str)
33656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	{
34656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_OCTET_STRING *os;
35656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
36656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	/* To a an object of OID 1.2.3.4.5, which is an octet string */
37656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	if (signed_string_nid == -1)
38656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		signed_string_nid=
39656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			OBJ_create("1.2.3.4.5","OID_example","Our example OID");
40656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	os=ASN1_OCTET_STRING_new();
41656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_OCTET_STRING_set(os,(unsigned char*)str,strlen(str));
42656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	/* When we add, we do not free */
43656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	PKCS7_add_signed_attribute(si,signed_string_nid,
44656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		V_ASN1_OCTET_STRING,(char *)os);
45656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	}
46656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
47656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Projectint get_signed_string(PKCS7_SIGNER_INFO *si, char *buf, int len)
48656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	{
49656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_TYPE *so;
50656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_OCTET_STRING *os;
51656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	int i;
52656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
53656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	if (signed_string_nid == -1)
54656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		signed_string_nid=
55656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			OBJ_create("1.2.3.4.5","OID_example","Our example OID");
56656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	/* To retrieve */
57656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	so=PKCS7_get_signed_attribute(si,signed_string_nid);
58656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	if (so != NULL)
59656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		{
60656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		if (so->type == V_ASN1_OCTET_STRING)
61656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			{
62656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			os=so->value.octet_string;
63656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			i=os->length;
64656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			if ((i+1) > len)
65656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project				i=len-1;
66656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			memcpy(buf,os->data,i);
67656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			return(i);
68656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			}
69656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		}
70656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	return(0);
71656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	}
72656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
73656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Projectstatic int signed_seq2string_nid= -1;
74656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project/* ########################################### */
75656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Projectint add_signed_seq2string(PKCS7_SIGNER_INFO *si, char *str1, char *str2)
76656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	{
77656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	/* To add an object of OID 1.9.999, which is a sequence containing
78656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	 * 2 octet strings */
79656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	unsigned char *p;
80656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_OCTET_STRING *os1,*os2;
81656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_STRING *seq;
82656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	unsigned char *data;
83656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	int i,total;
84656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
85656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	if (signed_seq2string_nid == -1)
86656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		signed_seq2string_nid=
87656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			OBJ_create("1.9.9999","OID_example","Our example OID");
88656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
89656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	os1=ASN1_OCTET_STRING_new();
90656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	os2=ASN1_OCTET_STRING_new();
91656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_OCTET_STRING_set(os1,(unsigned char*)str1,strlen(str1));
92656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_OCTET_STRING_set(os2,(unsigned char*)str1,strlen(str1));
93656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	i =i2d_ASN1_OCTET_STRING(os1,NULL);
94656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	i+=i2d_ASN1_OCTET_STRING(os2,NULL);
95656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	total=ASN1_object_size(1,i,V_ASN1_SEQUENCE);
96656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
97656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	data=malloc(total);
98656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	p=data;
99656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_put_object(&p,1,i,V_ASN1_SEQUENCE,V_ASN1_UNIVERSAL);
100656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	i2d_ASN1_OCTET_STRING(os1,&p);
101656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	i2d_ASN1_OCTET_STRING(os2,&p);
102656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
103656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	seq=ASN1_STRING_new();
104656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_STRING_set(seq,data,total);
105656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	free(data);
106656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_OCTET_STRING_free(os1);
107656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_OCTET_STRING_free(os2);
108656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
109656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	PKCS7_add_signed_attribute(si,signed_seq2string_nid,
110656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		V_ASN1_SEQUENCE,(char *)seq);
111656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	return(1);
112656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	}
113656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
114656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project/* For this case, I will malloc the return strings */
115656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Projectint get_signed_seq2string(PKCS7_SIGNER_INFO *si, char **str1, char **str2)
116656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	{
117656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_TYPE *so;
118656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
119656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	if (signed_seq2string_nid == -1)
120656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		signed_seq2string_nid=
121656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			OBJ_create("1.9.9999","OID_example","Our example OID");
122656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	/* To retrieve */
123656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	so=PKCS7_get_signed_attribute(si,signed_seq2string_nid);
124656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	if (so && (so->type == V_ASN1_SEQUENCE))
125656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		{
126656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		ASN1_const_CTX c;
127656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		ASN1_STRING *s;
128656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		long length;
129656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		ASN1_OCTET_STRING *os1,*os2;
130656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
131656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		s=so->value.sequence;
132656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		c.p=ASN1_STRING_data(s);
133656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		c.max=c.p+ASN1_STRING_length(s);
134656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		if (!asn1_GetSequence(&c,&length)) goto err;
135656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		/* Length is the length of the seqence */
136656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
137656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		c.q=c.p;
138656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		if ((os1=d2i_ASN1_OCTET_STRING(NULL,&c.p,c.slen)) == NULL)
139656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			goto err;
140656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		c.slen-=(c.p-c.q);
141656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
142656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		c.q=c.p;
143656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		if ((os2=d2i_ASN1_OCTET_STRING(NULL,&c.p,c.slen)) == NULL)
144656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			goto err;
145656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		c.slen-=(c.p-c.q);
146656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
147656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		if (!asn1_const_Finish(&c)) goto err;
148656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		*str1=malloc(os1->length+1);
149656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		*str2=malloc(os2->length+1);
150656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		memcpy(*str1,os1->data,os1->length);
151656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		memcpy(*str2,os2->data,os2->length);
152656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		(*str1)[os1->length]='\0';
153656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		(*str2)[os2->length]='\0';
154656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		ASN1_OCTET_STRING_free(os1);
155656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		ASN1_OCTET_STRING_free(os2);
156656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		return(1);
157656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		}
158656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Projecterr:
159656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	return(0);
160656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	}
161656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
162656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
163656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project/* #######################################
164656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project * THE OTHER WAY TO DO THINGS
165656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project * #######################################
166656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project */
167656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source ProjectX509_ATTRIBUTE *create_time(void)
168656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	{
169656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_UTCTIME *sign_time;
170656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	X509_ATTRIBUTE *ret;
171656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
172656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	/* The last parameter is the amount to add/subtract from the current
173656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	 * time (in seconds) */
174656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	sign_time=X509_gmtime_adj(NULL,0);
175656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ret=X509_ATTRIBUTE_create(NID_pkcs9_signingTime,
176656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		V_ASN1_UTCTIME,(char *)sign_time);
177656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	return(ret);
178656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	}
179656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
180656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source ProjectASN1_UTCTIME *sk_get_time(STACK_OF(X509_ATTRIBUTE) *sk)
181656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	{
182656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_TYPE *so;
183656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	PKCS7_SIGNER_INFO si;
184656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
185656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	si.auth_attr=sk;
186656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	so=PKCS7_get_signed_attribute(&si,NID_pkcs9_signingTime);
187656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	if (so->type == V_ASN1_UTCTIME)
188656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	    return so->value.utctime;
189656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	return NULL;
190656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	}
191656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
192656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source ProjectX509_ATTRIBUTE *create_string(char *str)
193656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	{
194656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_OCTET_STRING *os;
195656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	X509_ATTRIBUTE *ret;
196656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
197656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	/* To a an object of OID 1.2.3.4.5, which is an octet string */
198656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	if (signed_string_nid == -1)
199656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		signed_string_nid=
200656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			OBJ_create("1.2.3.4.5","OID_example","Our example OID");
201656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	os=ASN1_OCTET_STRING_new();
202656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_OCTET_STRING_set(os,(unsigned char*)str,strlen(str));
203656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	/* When we add, we do not free */
204656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ret=X509_ATTRIBUTE_create(signed_string_nid,
205656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		V_ASN1_OCTET_STRING,(char *)os);
206656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	return(ret);
207656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	}
208656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
209656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Projectint sk_get_string(STACK_OF(X509_ATTRIBUTE) *sk, char *buf, int len)
210656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	{
211656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_TYPE *so;
212656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_OCTET_STRING *os;
213656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	int i;
214656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	PKCS7_SIGNER_INFO si;
215656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
216656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	si.auth_attr=sk;
217656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
218656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	if (signed_string_nid == -1)
219656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		signed_string_nid=
220656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			OBJ_create("1.2.3.4.5","OID_example","Our example OID");
221656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	/* To retrieve */
222656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	so=PKCS7_get_signed_attribute(&si,signed_string_nid);
223656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	if (so != NULL)
224656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		{
225656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		if (so->type == V_ASN1_OCTET_STRING)
226656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			{
227656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			os=so->value.octet_string;
228656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			i=os->length;
229656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			if ((i+1) > len)
230656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project				i=len-1;
231656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			memcpy(buf,os->data,i);
232656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			return(i);
233656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			}
234656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		}
235656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	return(0);
236656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	}
237656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
238656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source ProjectX509_ATTRIBUTE *add_seq2string(PKCS7_SIGNER_INFO *si, char *str1, char *str2)
239656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	{
240656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	/* To add an object of OID 1.9.999, which is a sequence containing
241656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	 * 2 octet strings */
242656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	unsigned char *p;
243656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_OCTET_STRING *os1,*os2;
244656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_STRING *seq;
245656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	X509_ATTRIBUTE *ret;
246656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	unsigned char *data;
247656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	int i,total;
248656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
249656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	if (signed_seq2string_nid == -1)
250656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		signed_seq2string_nid=
251656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			OBJ_create("1.9.9999","OID_example","Our example OID");
252656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
253656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	os1=ASN1_OCTET_STRING_new();
254656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	os2=ASN1_OCTET_STRING_new();
255656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_OCTET_STRING_set(os1,(unsigned char*)str1,strlen(str1));
256656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_OCTET_STRING_set(os2,(unsigned char*)str1,strlen(str1));
257656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	i =i2d_ASN1_OCTET_STRING(os1,NULL);
258656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	i+=i2d_ASN1_OCTET_STRING(os2,NULL);
259656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	total=ASN1_object_size(1,i,V_ASN1_SEQUENCE);
260656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
261656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	data=malloc(total);
262656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	p=data;
263656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_put_object(&p,1,i,V_ASN1_SEQUENCE,V_ASN1_UNIVERSAL);
264656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	i2d_ASN1_OCTET_STRING(os1,&p);
265656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	i2d_ASN1_OCTET_STRING(os2,&p);
266656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
267656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	seq=ASN1_STRING_new();
268656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_STRING_set(seq,data,total);
269656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	free(data);
270656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_OCTET_STRING_free(os1);
271656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_OCTET_STRING_free(os2);
272656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
273656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ret=X509_ATTRIBUTE_create(signed_seq2string_nid,
274656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		V_ASN1_SEQUENCE,(char *)seq);
275656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	return(ret);
276656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	}
277656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
278656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project/* For this case, I will malloc the return strings */
279656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Projectint sk_get_seq2string(STACK_OF(X509_ATTRIBUTE) *sk, char **str1, char **str2)
280656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	{
281656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	ASN1_TYPE *so;
282656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	PKCS7_SIGNER_INFO si;
283656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
284656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	if (signed_seq2string_nid == -1)
285656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		signed_seq2string_nid=
286656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			OBJ_create("1.9.9999","OID_example","Our example OID");
287656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
288656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	si.auth_attr=sk;
289656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	/* To retrieve */
290656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	so=PKCS7_get_signed_attribute(&si,signed_seq2string_nid);
291656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	if (so->type == V_ASN1_SEQUENCE)
292656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		{
293656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		ASN1_const_CTX c;
294656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		ASN1_STRING *s;
295656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		long length;
296656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		ASN1_OCTET_STRING *os1,*os2;
297656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
298656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		s=so->value.sequence;
299656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		c.p=ASN1_STRING_data(s);
300656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		c.max=c.p+ASN1_STRING_length(s);
301656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		if (!asn1_GetSequence(&c,&length)) goto err;
302656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		/* Length is the length of the seqence */
303656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
304656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		c.q=c.p;
305656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		if ((os1=d2i_ASN1_OCTET_STRING(NULL,&c.p,c.slen)) == NULL)
306656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			goto err;
307656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		c.slen-=(c.p-c.q);
308656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
309656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		c.q=c.p;
310656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		if ((os2=d2i_ASN1_OCTET_STRING(NULL,&c.p,c.slen)) == NULL)
311656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project			goto err;
312656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		c.slen-=(c.p-c.q);
313656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
314656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		if (!asn1_const_Finish(&c)) goto err;
315656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		*str1=malloc(os1->length+1);
316656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		*str2=malloc(os2->length+1);
317656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		memcpy(*str1,os1->data,os1->length);
318656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		memcpy(*str2,os2->data,os2->length);
319656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		(*str1)[os1->length]='\0';
320656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		(*str2)[os2->length]='\0';
321656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		ASN1_OCTET_STRING_free(os1);
322656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		ASN1_OCTET_STRING_free(os2);
323656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		return(1);
324656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project		}
325656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Projecterr:
326656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	return(0);
327656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project	}
328656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
329656d9c7f52f88b3a3daccafa7655dec086c4756eThe Android Open Source Project
330