Skip to content

Commit

Permalink
Bug 1531236 - Accessor for certificate DER, r=jcj
Browse files Browse the repository at this point in the history
Summary:
Forgot to put this up.  This will make the neqo wrapper considerably more
hygenic.  Having to explode the entire CERTCertificate struct (which is public
and never should have been) into the FFI is a complete disaster.  Better to
treat it as opaque and use an accessor function.

Reviewers: jcj

Tags: #secure-revision

Bug #: 1531236

Differential Revision: https://phabricator.services.mozilla.com/D24129

--HG--
extra : rebase_source : cc0c75ba0153307ae7138ae6cf1953e3584f8345
  • Loading branch information
martinthomson committed Feb 28, 2019
1 parent f572a15 commit b7b584f
Show file tree
Hide file tree
Showing 7 changed files with 77 additions and 0 deletions.
5 changes: 5 additions & 0 deletions automation/abi-check/expected-report-libnss3.so.txt
@@ -0,0 +1,5 @@

1 Added function:

'function SECStatus CERT_GetCertificateDer(const CERTCertificate*, SECItem*)' {CERT_GetCertificateDer@@NSS_3.44}

47 changes: 47 additions & 0 deletions gtests/certdb_gtest/cert_unittest.cc
@@ -0,0 +1,47 @@
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* vim: set ts=2 et sw=2 tw=80: */
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this file,
* You can obtain one at http://mozilla.org/MPL/2.0/. */

#include "gtest/gtest.h"

#include "nss.h"
#include "secerr.h"
#include "pk11pub.h"
#include "nss_scoped_ptrs.h"

namespace nss_test {

class CertTest : public ::testing::Test {};

// Tests CERT_GetCertificateDer for the certs we have.
TEST_F(CertTest, GetCertDer) {
// Listing all the certs should get us the default trust anchors.
ScopedCERTCertList certs(PK11_ListCerts(PK11CertListAll, nullptr));
ASSERT_FALSE(PR_CLIST_IS_EMPTY(&certs->list));

for (PRCList* cursor = PR_NEXT_LINK(&certs->list); cursor != &certs->list;
cursor = PR_NEXT_LINK(cursor)) {
CERTCertListNode* node = (CERTCertListNode*)cursor;
SECItem der;
ASSERT_EQ(SECSuccess, CERT_GetCertificateDer(node->cert, &der));
ASSERT_EQ(0, SECITEM_CompareItem(&der, &node->cert->derCert));
}
}

TEST_F(CertTest, GetCertDerBad) {
EXPECT_EQ(SECFailure, CERT_GetCertificateDer(nullptr, nullptr));
EXPECT_EQ(SEC_ERROR_INVALID_ARGS, PORT_GetError());

ScopedCERTCertList certs(PK11_ListCerts(PK11CertListAll, nullptr));
ASSERT_FALSE(PR_CLIST_IS_EMPTY(&certs->list));
CERTCertListNode* node = (CERTCertListNode*)PR_NEXT_LINK(&certs->list);
EXPECT_EQ(SECFailure, CERT_GetCertificateDer(node->cert, nullptr));
EXPECT_EQ(SEC_ERROR_INVALID_ARGS, PORT_GetError());

SECItem der;
EXPECT_EQ(SECFailure, CERT_GetCertificateDer(nullptr, &der));
EXPECT_EQ(SEC_ERROR_INVALID_ARGS, PORT_GetError());
}
}
1 change: 1 addition & 0 deletions gtests/certdb_gtest/certdb_gtest.gyp
Expand Up @@ -12,6 +12,7 @@
'type': 'executable',
'sources': [
'alg1485_unittest.cc',
'cert_unittest.cc',
'decode_certs_unittest.cc',
'<(DEPTH)/gtests/common/gtests.cc'
],
Expand Down
1 change: 1 addition & 0 deletions gtests/certdb_gtest/manifest.mn
Expand Up @@ -8,6 +8,7 @@ MODULE = nss

CPPSRCS = \
alg1485_unittest.cc \
cert_unittest.cc \
decode_certs_unittest.cc \
$(NULL)

Expand Down
6 changes: 6 additions & 0 deletions lib/certdb/cert.h
Expand Up @@ -215,6 +215,12 @@ extern void CERT_DestroyCertificate(CERTCertificate *cert);
*/
extern CERTCertificate *CERT_DupCertificate(CERTCertificate *c);

/* Access the DER of the certificate. This only creates a reference to the DER
* in the outparam not a copy. To avoid the pointer becoming invalid, use
* CERT_DupCertificate() and keep a reference to the duplicate alive.
*/
extern SECStatus CERT_GetCertificateDer(const CERTCertificate *c, SECItem *der);

/*
** Create a new certificate request. This result must be wrapped with an
** CERTSignedData to create a signed certificate request.
Expand Down
11 changes: 11 additions & 0 deletions lib/certdb/certdb.c
Expand Up @@ -1314,6 +1314,17 @@ CERT_DupCertificate(CERTCertificate *c)
return c;
}

SECStatus
CERT_GetCertificateDer(const CERTCertificate *c, SECItem *der)
{
if (!c || !der) {
PORT_SetError(SEC_ERROR_INVALID_ARGS);
return SECFailure;
}
*der = c->derCert;
return SECSuccess;
}

/*
* Allow use of default cert database, so that apps(such as mozilla) don't
* have to pass the handle all over the place.
Expand Down
6 changes: 6 additions & 0 deletions lib/nss/nss.def
Expand Up @@ -1145,3 +1145,9 @@ HASH_GetHashOidTagByHashType;
;+ local:
;+ *;
;+};
;+NSS_3.44 { # NSS 3.44 release
;+ global:
CERT_GetCertificateDer;
;+ local:
;+ *;
;+};

0 comments on commit b7b584f

Please sign in to comment.