monotone

monotone Mtn Source Tree

Root/botan/pkcs10.cpp

1/*************************************************
2* PKCS #10 Source File *
3* (C) 1999-2007 The Botan Project *
4*************************************************/
5
6#include <botan/pkcs10.h>
7#include <botan/der_enc.h>
8#include <botan/ber_dec.h>
9#include <botan/parsing.h>
10#include <botan/x509stor.h>
11#include <botan/x509_ext.h>
12#include <botan/oids.h>
13#include <botan/pem.h>
14
15namespace Botan {
16
17/*************************************************
18* PKCS10_Request Constructor *
19*************************************************/
20PKCS10_Request::PKCS10_Request(DataSource& in) :
21 X509_Object(in, "CERTIFICATE REQUEST/NEW CERTIFICATE REQUEST")
22 {
23 do_decode();
24 }
25
26/*************************************************
27* PKCS10_Request Constructor *
28*************************************************/
29PKCS10_Request::PKCS10_Request(const std::string& in) :
30 X509_Object(in, "CERTIFICATE REQUEST/NEW CERTIFICATE REQUEST")
31 {
32 do_decode();
33 }
34
35/*************************************************
36* Deocde the CertificateRequestInfo *
37*************************************************/
38void PKCS10_Request::force_decode()
39 {
40 BER_Decoder cert_req_info(tbs_bits);
41
42 u32bit version;
43 cert_req_info.decode(version);
44 if(version != 0)
45 throw Decoding_Error("Unknown version code in PKCS #10 request: " +
46 to_string(version));
47
48 X509_DN dn_subject;
49 cert_req_info.decode(dn_subject);
50
51 info.add(dn_subject.contents());
52
53 BER_Object public_key = cert_req_info.get_next_object();
54 if(public_key.type_tag != SEQUENCE || public_key.class_tag != CONSTRUCTED)
55 throw BER_Bad_Tag("PKCS10_Request: Unexpected tag for public key",
56 public_key.type_tag, public_key.class_tag);
57
58 info.add("X509.Certificate.public_key",
59 PEM_Code::encode(
60 ASN1::put_in_sequence(public_key.value),
61 "PUBLIC KEY"
62 )
63 );
64
65 BER_Object attr_bits = cert_req_info.get_next_object();
66
67 if(attr_bits.type_tag == 0 &&
68 attr_bits.class_tag == ASN1_Tag(CONSTRUCTED | CONTEXT_SPECIFIC))
69 {
70 BER_Decoder attributes(attr_bits.value);
71 while(attributes.more_items())
72 {
73 Attribute attr;
74 attributes.decode(attr);
75 handle_attribute(attr);
76 }
77 attributes.verify_end();
78 }
79 else if(attr_bits.type_tag != NO_OBJECT)
80 throw BER_Bad_Tag("PKCS10_Request: Unexpected tag for attributes",
81 attr_bits.type_tag, attr_bits.class_tag);
82
83 cert_req_info.verify_end();
84
85 X509_Code sig_check = X509_Store::check_sig(*this, subject_public_key());
86 if(sig_check != VERIFIED)
87 throw Decoding_Error("PKCS #10 request: Bad signature detected");
88 }
89
90/*************************************************
91* Handle attributes in a PKCS #10 request *
92*************************************************/
93void PKCS10_Request::handle_attribute(const Attribute& attr)
94 {
95 BER_Decoder value(attr.parameters);
96
97 if(attr.oid == OIDS::lookup("PKCS9.EmailAddress"))
98 {
99 ASN1_String email;
100 value.decode(email);
101 info.add("RFC822", email.value());
102 }
103 else if(attr.oid == OIDS::lookup("PKCS9.ChallengePassword"))
104 {
105 ASN1_String challenge_password;
106 value.decode(challenge_password);
107 info.add("PKCS9.ChallengePassword", challenge_password.value());
108 }
109 else if(attr.oid == OIDS::lookup("PKCS9.ExtensionRequest"))
110 {
111 Extensions extensions;
112 value.decode(extensions).verify_end();
113
114 Data_Store issuer_info;
115 extensions.contents_to(info, issuer_info);
116 }
117 }
118
119/*************************************************
120* Return the challenge password (if any) *
121*************************************************/
122std::string PKCS10_Request::challenge_password() const
123 {
124 return info.get1("PKCS9.ChallengePassword");
125 }
126
127/*************************************************
128* Return the name of the requestor *
129*************************************************/
130X509_DN PKCS10_Request::subject_dn() const
131 {
132 return create_dn(info);
133 }
134
135/*************************************************
136* Return the public key of the requestor *
137*************************************************/
138MemoryVector<byte> PKCS10_Request::raw_public_key() const
139 {
140 DataSource_Memory source(info.get1("X509.Certificate.public_key"));
141 return PEM_Code::decode_check_label(source, "PUBLIC KEY");
142 }
143
144/*************************************************
145* Return the public key of the requestor *
146*************************************************/
147Public_Key* PKCS10_Request::subject_public_key() const
148 {
149 DataSource_Memory source(info.get1("X509.Certificate.public_key"));
150 return X509::load_key(source);
151 }
152
153/*************************************************
154* Return the alternative names of the requestor *
155*************************************************/
156AlternativeName PKCS10_Request::subject_alt_name() const
157 {
158 return create_alt_name(info);
159 }
160
161/*************************************************
162* Return the key constraints (if any) *
163*************************************************/
164Key_Constraints PKCS10_Request::constraints() const
165 {
166 return Key_Constraints(info.get1_u32bit("X509v3.KeyUsage", NO_CONSTRAINTS));
167 }
168
169/*************************************************
170* Return the extendend key constraints (if any) *
171*************************************************/
172std::vector<OID> PKCS10_Request::ex_constraints() const
173 {
174 std::vector<std::string> oids = info.get("X509v3.ExtendedKeyUsage");
175
176 std::vector<OID> result;
177 for(u32bit j = 0; j != oids.size(); ++j)
178 result.push_back(OID(oids[j]));
179 return result;
180 }
181
182/*************************************************
183* Return is a CA certificate is requested *
184*************************************************/
185bool PKCS10_Request::is_CA() const
186 {
187 return info.get1_u32bit("X509v3.BasicConstraints.is_ca");
188 }
189
190/*************************************************
191* Return the desired path limit (if any) *
192*************************************************/
193u32bit PKCS10_Request::path_limit() const
194 {
195 return info.get1_u32bit("X509v3.BasicConstraints.path_constraint", 0);
196 }
197
198}

Archive Download this file

Branches

Tags

Quick Links:     www.monotone.ca    -     Downloads    -     Documentation    -     Wiki    -     Code Forge    -     Build Status