blob: 170bc7a1206bad0394614fff7170c38441fb4ac9 [file] [log] [blame]
[email protected]0fd776c42010-09-29 21:59:171// Copyright (c) 2010 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/browser/certificate_manager_model.h"
6
7#include <cert.h>
8
9#include "base/i18n/time_formatting.h"
10#include "base/logging.h"
11#include "base/utf_string_conversions.h"
12#include "chrome/third_party/mozilla_security_manager/nsNSSCertHelper.h"
13#include "chrome/third_party/mozilla_security_manager/nsNSSCertificate.h"
14#include "net/base/x509_certificate.h"
15
16// TODO(mattm): Try to make this use only X509Certificate stuff rather than NSS
17// functions in some places. (Not very important at this time since this is only
18// used w/NSS anyway.)
19
20// PSM = Mozilla's Personal Security Manager.
21namespace psm = mozilla_security_manager;
22
23namespace {
24
25// Convert a char* return value from NSS into a std::string and free the NSS
26// memory. If the arg is NULL, an empty string will be returned instead.
27std::string Stringize(char* nss_text) {
28 std::string s;
29 if (nss_text) {
30 s = nss_text;
31 PORT_Free(nss_text);
32 }
33 return s;
34}
35
36std::string GetCertNameOrNickname(CERTCertificate* os_cert) {
37 std::string name = psm::ProcessIDN(
38 Stringize(CERT_GetCommonName(&os_cert->subject)));
39 if (name.empty() && os_cert->nickname) {
40 name = os_cert->nickname;
41 // Hack copied from mozilla: Cut off text before first :, which seems to
42 // just be the token name.
43 size_t colon_pos = name.find(':');
44 if (colon_pos != std::string::npos)
45 name = name.substr(colon_pos + 1);
46 }
47 return name;
48}
49
50} // namespace
51
52CertificateManagerModel::CertificateManagerModel() {
53}
54
55CertificateManagerModel::~CertificateManagerModel() {
56}
57
58void CertificateManagerModel::Refresh() {
59 cert_db_.ListCerts(&cert_list_);
60}
61
62void CertificateManagerModel::FilterAndBuildOrgGroupingMap(
63 net::CertType filter_type,
64 CertificateManagerModel::OrgGroupingMap* map) const {
65 for (net::CertificateList::const_iterator i = cert_list_.begin();
66 i != cert_list_.end(); ++i) {
67 net::X509Certificate* cert = i->get();
68 net::CertType type = psm::GetCertType(cert->os_cert_handle());
69 if (type != filter_type)
70 continue;
71
72 std::string org;
73 if (!cert->subject().organization_names.empty())
74 org = cert->subject().organization_names[0];
75 if (org.empty())
76 org = cert->subject().GetDisplayName();
77
78 (*map)[org].push_back(cert);
79 }
80}
81
82string16 CertificateManagerModel::GetColumnText(
83 const net::X509Certificate& cert,
84 Column column) const {
85 string16 rv;
86 switch (column) {
87 case COL_SUBJECT_NAME:
88 rv = UTF8ToUTF16(GetCertNameOrNickname(cert.os_cert_handle()));
89 break;
90 case COL_CERTIFICATE_STORE:
91 rv = UTF8ToUTF16(psm::GetCertTokenName(cert.os_cert_handle()));
92 break;
93 case COL_SERIAL_NUMBER:
94 rv = ASCIIToUTF16(Stringize(CERT_Hexify(
95 &cert.os_cert_handle()->serialNumber, PR_TRUE)));
96 break;
97 case COL_EXPIRES_ON:
98 if (!cert.valid_expiry().is_null()) {
99 rv = WideToUTF16Hack(
100 base::TimeFormatShortDateNumeric(cert.valid_expiry()));
101 }
102 break;
103 case COL_EMAIL_ADDRESS:
104 if (cert.os_cert_handle()->emailAddr)
105 rv = UTF8ToUTF16(cert.os_cert_handle()->emailAddr);
106 break;
107 default:
108 NOTREACHED();
109 }
110 return rv;
111}