1// Copyright (c) 2011 The Chromium Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#include "chrome/common/net/x509_certificate_model.h"
6
7#include <openssl/obj_mac.h>
8#include <openssl/sha.h>
9#include <openssl/x509v3.h>
10
11#include "base/logging.h"
12#include "base/string_number_conversions.h"
13#include "net/base/x509_openssl_util.h"
14
15namespace nxou = net::x509_openssl_util;
16
17namespace {
18
19std::string AlternativeWhenEmpty(const std::string& text,
20                                 const std::string& alternative) {
21  return text.empty() ? alternative : text;
22}
23
24std::string GetKeyValuesFromName(X509_NAME* name) {
25  std::string ret;
26  int rdns = X509_NAME_entry_count(name) - 1;
27  for (int i = rdns; i >= 0; --i) {
28    std::string key;
29    std::string value;
30    if (!nxou::ParsePrincipalKeyAndValueByIndex(name, i, &key, &value))
31      break;
32    ret += key;
33    ret += " = ";
34    ret += value;
35    ret += '\n';
36  }
37  return ret;
38}
39
40}  // namepsace
41
42namespace x509_certificate_model {
43
44using net::X509Certificate;
45
46std::string GetCertNameOrNickname(X509Certificate::OSCertHandle cert_handle) {
47  // TODO(bulach): implement me.
48  return "";
49}
50
51std::string GetNickname(X509Certificate::OSCertHandle cert_handle) {
52  // TODO(jamescook): implement me.
53  return "";
54}
55
56std::string GetTokenName(X509Certificate::OSCertHandle cert_handle) {
57  // TODO(bulach): implement me.
58  return "";
59}
60
61std::string GetVersion(net::X509Certificate::OSCertHandle cert_handle) {
62  unsigned long version = X509_get_version(cert_handle);
63  if (version != ULONG_MAX)
64    return base::UintToString(version + 1);
65  return "";
66}
67
68net::CertType GetType(X509Certificate::OSCertHandle os_cert) {
69  // TODO(bulach): implement me.
70  return net::UNKNOWN_CERT;
71}
72
73std::string GetEmailAddress(X509Certificate::OSCertHandle os_cert) {
74  // TODO(bulach): implement me.
75  return "";
76}
77
78void GetUsageStrings(X509Certificate::OSCertHandle cert_handle,
79                         std::vector<std::string>* usages) {
80  // TODO(bulach): implement me.
81}
82
83std::string GetKeyUsageString(X509Certificate::OSCertHandle cert_handle) {
84  // TODO(bulach): implement me.
85  return "";
86}
87
88std::string GetSerialNumberHexified(
89    X509Certificate::OSCertHandle cert_handle,
90    const std::string& alternative_text) {
91  ASN1_INTEGER* num = X509_get_serialNumber(cert_handle);
92  const char kSerialNumberSeparator = ':';
93  std::string hex_string = ProcessRawBytesWithSeparators(
94      num->data, num->length, kSerialNumberSeparator, kSerialNumberSeparator);
95  return AlternativeWhenEmpty(hex_string, alternative_text);
96}
97
98std::string GetIssuerCommonName(
99    X509Certificate::OSCertHandle cert_handle,
100    const std::string& alternative_text) {
101  std::string ret;
102  nxou::ParsePrincipalValueByNID(X509_get_issuer_name(cert_handle),
103                                 NID_commonName, &ret);
104  return AlternativeWhenEmpty(ret, alternative_text);
105}
106
107std::string GetIssuerOrgName(
108    X509Certificate::OSCertHandle cert_handle,
109    const std::string& alternative_text) {
110  std::string ret;
111  nxou::ParsePrincipalValueByNID(X509_get_issuer_name(cert_handle),
112                                 NID_organizationName, &ret);
113  return AlternativeWhenEmpty(ret, alternative_text);
114}
115
116std::string GetIssuerOrgUnitName(
117    X509Certificate::OSCertHandle cert_handle,
118    const std::string& alternative_text) {
119  std::string ret;
120  nxou::ParsePrincipalValueByNID(X509_get_issuer_name(cert_handle),
121                                 NID_organizationalUnitName, &ret);
122  return AlternativeWhenEmpty(ret, alternative_text);
123}
124
125std::string GetSubjectOrgName(
126    X509Certificate::OSCertHandle cert_handle,
127    const std::string& alternative_text) {
128  std::string ret;
129  nxou::ParsePrincipalValueByNID(X509_get_subject_name(cert_handle),
130                                 NID_organizationName, &ret);
131  return AlternativeWhenEmpty(ret, alternative_text);
132}
133
134std::string GetSubjectOrgUnitName(
135    X509Certificate::OSCertHandle cert_handle,
136    const std::string& alternative_text) {
137  std::string ret;
138  nxou::ParsePrincipalValueByNID(X509_get_subject_name(cert_handle),
139                                 NID_organizationalUnitName, &ret);
140  return AlternativeWhenEmpty(ret, alternative_text);
141}
142
143std::string GetSubjectCommonName(X509Certificate::OSCertHandle cert_handle,
144                                 const std::string& alternative_text) {
145  std::string ret;
146  nxou::ParsePrincipalValueByNID(X509_get_subject_name(cert_handle),
147                                 NID_commonName, &ret);
148  return AlternativeWhenEmpty(ret, alternative_text);
149}
150
151bool GetTimes(X509Certificate::OSCertHandle cert_handle,
152              base::Time* issued, base::Time* expires) {
153  return nxou::ParseDate(X509_get_notBefore(cert_handle), issued) &&
154         nxou::ParseDate(X509_get_notAfter(cert_handle), expires);
155}
156
157std::string GetTitle(net::X509Certificate::OSCertHandle cert_handle) {
158  // TODO(bulach): implement me.
159  return "";
160}
161
162std::string GetIssuerName(net::X509Certificate::OSCertHandle cert_handle) {
163  return GetKeyValuesFromName(X509_get_issuer_name(cert_handle));
164}
165
166std::string GetSubjectName(net::X509Certificate::OSCertHandle cert_handle) {
167  return GetKeyValuesFromName(X509_get_subject_name(cert_handle));
168}
169
170void GetEmailAddresses(net::X509Certificate::OSCertHandle cert_handle,
171                       std::vector<std::string>* email_addresses) {
172  // TODO(bulach): implement me.
173}
174
175void GetNicknameStringsFromCertList(
176    const std::vector<scoped_refptr<net::X509Certificate> >& certs,
177    const std::string& cert_expired,
178    const std::string& cert_not_yet_valid,
179    std::vector<std::string>* nick_names) {
180  // TODO(bulach): implement me.
181}
182
183std::string GetPkcs11Id(net::X509Certificate::OSCertHandle cert_handle) {
184  // TODO(jamescook): implement me.
185  return "";
186}
187
188void GetExtensions(
189    const std::string& critical_label,
190    const std::string& non_critical_label,
191    net::X509Certificate::OSCertHandle cert_handle,
192    Extensions* extensions) {
193  // TODO(bulach): implement me.
194}
195
196std::string HashCertSHA256(net::X509Certificate::OSCertHandle cert_handle) {
197  unsigned char sha256_data[SHA256_DIGEST_LENGTH] = {0};
198  unsigned int sha256_size = sizeof(sha256_data);
199  int ret = X509_digest(cert_handle, EVP_sha256(), sha256_data, &sha256_size);
200  CHECK(ret);
201  CHECK_EQ(sha256_size, sizeof(sha256_data));
202  return ProcessRawBytes(sha256_data, sha256_size);
203}
204
205std::string HashCertSHA1(net::X509Certificate::OSCertHandle cert_handle) {
206  unsigned char sha1_data[SHA_DIGEST_LENGTH] = {0};
207  unsigned int sha1_size = sizeof(sha1_data);
208  int ret = X509_digest(cert_handle, EVP_sha1(), sha1_data, &sha1_size);
209  CHECK(ret);
210  CHECK_EQ(sha1_size, sizeof(sha1_data));
211  return ProcessRawBytes(sha1_data, sha1_size);
212}
213
214void GetCertChainFromCert(net::X509Certificate::OSCertHandle cert_handle,
215                          net::X509Certificate::OSCertHandles* cert_handles) {
216  // TODO(bulach): how to get the chain out of a certificate?
217  cert_handles->push_back(net::X509Certificate::DupOSCertHandle(cert_handle));
218}
219
220void DestroyCertChain(net::X509Certificate::OSCertHandles* cert_handles) {
221  for (net::X509Certificate::OSCertHandles::iterator i = cert_handles->begin();
222       i != cert_handles->end(); ++i)
223    X509_free(*i);
224  cert_handles->clear();
225}
226
227std::string GetDerString(net::X509Certificate::OSCertHandle cert_handle) {
228  // TODO(bulach): implement me.
229  return "";
230}
231
232std::string GetCMSString(const net::X509Certificate::OSCertHandles& cert_chain,
233                         size_t start, size_t end) {
234  // TODO(bulach): implement me.
235  return "";
236}
237
238std::string ProcessSecAlgorithmSignature(
239    net::X509Certificate::OSCertHandle cert_handle) {
240  // TODO(bulach): implement me.
241  return "";
242}
243
244std::string ProcessSecAlgorithmSubjectPublicKey(
245    net::X509Certificate::OSCertHandle cert_handle) {
246  // TODO(bulach): implement me.
247  return "";
248}
249
250std::string ProcessSecAlgorithmSignatureWrap(
251    net::X509Certificate::OSCertHandle cert_handle) {
252  // TODO(bulach): implement me.
253  return "";
254}
255
256std::string ProcessSubjectPublicKeyInfo(
257    net::X509Certificate::OSCertHandle cert_handle) {
258  // TODO(bulach): implement me.
259  return "";
260}
261
262std::string ProcessRawBitsSignatureWrap(
263    net::X509Certificate::OSCertHandle cert_handle) {
264  // TODO(bulach): implement me.
265  return "";
266}
267
268void RegisterDynamicOids() {
269}
270
271}  // namespace x509_certificate_model
272