[poppler] poppler/SignatureHandler.cc poppler/SignatureHandler.h poppler/SignatureInfo.cc utils/pdfsig.1 utils/pdfsig.cc
GitLab Mirror
gitlab-mirror at kemper.freedesktop.org
Thu Jan 24 14:41:28 UTC 2019
poppler/SignatureHandler.cc | 56 +++++++++++++++++++++++++++++---------------
poppler/SignatureHandler.h | 9 ++++---
poppler/SignatureInfo.cc | 4 +--
utils/pdfsig.1 | 15 ++++++++++-
utils/pdfsig.cc | 12 +++++++--
5 files changed, 68 insertions(+), 28 deletions(-)
New commits:
commit 7486e4995d66f1a8676f3e65e408e8cdab049f6b
Author: Albert Astals Cid <aacid at kde.org>
Date: Wed Jan 16 22:56:42 2019 +0100
pdfsig: add -nssdir option
Contains code inspired in code by Hans-Ulrich Jüttner and Adrian Johnson
diff --git a/poppler/SignatureHandler.cc b/poppler/SignatureHandler.cc
index f616afbb..18033b48 100644
--- a/poppler/SignatureHandler.cc
+++ b/poppler/SignatureHandler.cc
@@ -45,7 +45,7 @@ unsigned int SignatureHandler::digestLength(SECOidTag digestAlgId)
char *SignatureHandler::getSignerName()
{
- if (!CMSSignerInfo)
+ if (!CMSSignerInfo || !NSS_IsInitialized())
return nullptr;
CERTCertificate *cert = NSS_CMSSignerInfo_GetSigningCertificate(CMSSignerInfo, CERT_GetDefaultCertDB());
@@ -182,8 +182,7 @@ std::unique_ptr<X509CertificateInfo> SignatureHandler::getCertificateInfo() cons
return certInfo;
}
-
-GooString *SignatureHandler::getDefaultFirefoxCertDB_Linux()
+static GooString *getDefaultFirefoxCertDB_Linux()
{
GooString * finalPath = nullptr;
DIR *toSearchIn;
@@ -215,27 +214,45 @@ GooString *SignatureHandler::getDefaultFirefoxCertDB_Linux()
/**
* Initialise NSS
*/
-void SignatureHandler::init_nss()
+void SignatureHandler::setNSSDir(const GooString &nssDir)
{
- GooString *certDBPath = getDefaultFirefoxCertDB_Linux();
+ static bool setNssDirCalled = false;
+
+ if (NSS_IsInitialized() && nssDir.getLength() > 0) {
+ error(errInternal, 0, "You need to call setNSSDir before signature validation related operations happen");
+ return;
+ }
+
+ if (setNssDirCalled)
+ return;
+
+ setNssDirCalled = true;
+
bool initSuccess = false;
- if (certDBPath == nullptr) {
- initSuccess = (NSS_Init("sql:/etc/pki/nssdb") == SECSuccess);
+ if (nssDir.getLength() > 0) {
+ initSuccess = (NSS_Init(nssDir.c_str()) == SECSuccess);
} else {
- initSuccess = (NSS_Init(certDBPath->c_str()) == SECSuccess);
- }
- if (!initSuccess) {
- GooString homeNssDb(getenv("HOME"));
- homeNssDb.append("/.pki/nssdb");
- initSuccess = (NSS_Init(homeNssDb.c_str()) == SECSuccess);
+ GooString *certDBPath = getDefaultFirefoxCertDB_Linux();
+ if (certDBPath == nullptr) {
+ initSuccess = (NSS_Init("sql:/etc/pki/nssdb") == SECSuccess);
+ } else {
+ initSuccess = (NSS_Init(certDBPath->c_str()) == SECSuccess);
+ }
if (!initSuccess) {
- NSS_NoDB_Init(nullptr);
+ GooString homeNssDb(getenv("HOME"));
+ homeNssDb.append("/.pki/nssdb");
+ initSuccess = (NSS_Init(homeNssDb.c_str()) == SECSuccess);
+ if (!initSuccess) {
+ NSS_NoDB_Init(nullptr);
+ }
}
+ delete certDBPath;
}
- //Make sure NSS root certificates module is loaded
- SECMOD_AddNewModule("Root Certs", "libnssckbi.so", 0, 0);
- delete certDBPath;
+ if (initSuccess) {
+ //Make sure NSS root certificates module is loaded
+ SECMOD_AddNewModule("Root Certs", "libnssckbi.so", 0, 0);
+ }
}
@@ -246,7 +263,7 @@ SignatureHandler::SignatureHandler(unsigned char *p7, int p7_length)
CMSSignerInfo(nullptr),
temp_certs(nullptr)
{
- init_nss();
+ setNSSDir({});
CMSitem.data = p7;
CMSitem.len = p7_length;
CMSMessage = CMS_MessageCreate(&CMSitem);
@@ -377,6 +394,9 @@ SignatureValidationStatus SignatureHandler::validateSignature()
if (!CMSSignedData)
return SIGNATURE_GENERIC_ERROR;
+ if (!NSS_IsInitialized())
+ return SIGNATURE_GENERIC_ERROR;
+
digest_buffer = (unsigned char *)PORT_Alloc(hash_length);
unsigned int result_len = 0;
diff --git a/poppler/SignatureHandler.h b/poppler/SignatureHandler.h
index f49d4286..40ca990c 100644
--- a/poppler/SignatureHandler.h
+++ b/poppler/SignatureHandler.h
@@ -49,13 +49,16 @@ public:
CertificateValidationStatus validateCertificate(time_t validation_time);
std::unique_ptr<X509CertificateInfo> getCertificateInfo() const;
+ // Initializes the NSS dir with the custom given directory
+ // calling it with an empty string means use the default firefox db, /etc/pki/nssdb, ~/.pki/nssdb
+ // If you don't want a custom NSS dir and the default entries are fine for you, not calling this function is fine
+ // If wanted, this has to be called before doing signature validation calls
+ static void setNSSDir(const GooString &nssDir);
+
private:
SignatureHandler(const SignatureHandler &);
SignatureHandler& operator=(const SignatureHandler &);
- void init_nss();
-
- GooString * getDefaultFirefoxCertDB_Linux();
unsigned int digestLength(SECOidTag digestAlgId);
NSSCMSMessage *CMS_MessageCreate(SECItem * cms_item);
NSSCMSSignedData *CMS_SignedDataCreate(NSSCMSMessage * cms_msg);
diff --git a/poppler/SignatureInfo.cc b/poppler/SignatureInfo.cc
index b48ce146..3ab6f91f 100644
--- a/poppler/SignatureInfo.cc
+++ b/poppler/SignatureInfo.cc
@@ -7,7 +7,7 @@
// Copyright 2015 André Guerreiro <aguerreiro1985 at gmail.com>
// Copyright 2015 André Esser <bepandre at hotmail.com>
// Copyright 2017 Hans-Ulrich Jüttner <huj at froreich-bioscientia.de>
-// Copyright 2017, 2018 Albert Astals Cid <aacid at kde.org>
+// Copyright 2017-2019 Albert Astals Cid <aacid at kde.org>
// Copyright 2018 Chinmoy Ranjan Pradhan <chinmoyrp65 at protonmail.com>
// Copyright 2018 Oliver Sander <oliver.sander at tu-dresden.de>
//
@@ -133,7 +133,7 @@ void SignatureInfo::setSignerName(char *signerName)
void SignatureInfo::setSubjectDN(const char *subjectDN)
{
free(subject_dn);
- subject_dn = strdup(subjectDN);
+ subject_dn = subjectDN ? strdup(subjectDN) : nullptr;
}
void SignatureInfo::setLocation(const char *loc)
diff --git a/utils/pdfsig.1 b/utils/pdfsig.1
index 0a5cc62d..3567e96c 100644
--- a/utils/pdfsig.1
+++ b/utils/pdfsig.1
@@ -15,13 +15,23 @@ the time and date of the signature, the hash algorithm used for signing,
the type of the signature as stated in the PDF and
the signed ranges with a statement wether the total document is signed.
.PP
-The signer certificate validation uses the trusted certificates stored in the following locations:
+The signer certificate validation uses the trusted certificates stored in the
+Network Security Services (NSS) Database. The NSS Database is searched for in the following locations:
.IP \(bu
-The NSS Certificate database in the default Firefox profile.
+If the \-nssdir option is specified, the directory specified by this option.
+.IP \(bu
+The NSS Certificate database in the default Firefox profile. i.e. $HOME/.mozilla/firefox/*.default.
.IP \(bu
The NSS Certificate database in /etc/pki/nssdb.
.SH OPTIONS
.TP
+.B \-nssdir "[prefix]directory"
+Specify the database directory containing the certificate and key
+database files. See certutil(1) -d option for details of the
+prefix. If not specified the other search locations described in
+.B DESCRIPTION
+are used.
+.TP
.B \-nocert
Do not validate the certificate.
.TP
@@ -52,3 +62,4 @@ and copyright 2005-2015 The Poppler Developers - http://poppler.freedesktop.org
.BR pdftotext (1)
.BR pdfseparate (1),
.BR pdfunite (1)
+.BR certutil (1)
diff --git a/utils/pdfsig.cc b/utils/pdfsig.cc
index 82c0616b..64299690 100644
--- a/utils/pdfsig.cc
+++ b/utils/pdfsig.cc
@@ -6,10 +6,10 @@
//
// Copyright 2015 André Guerreiro <aguerreiro1985 at gmail.com>
// Copyright 2015 André Esser <bepandre at hotmail.com>
-// Copyright 2015, 2017, 2018 Albert Astals Cid <aacid at kde.org>
+// Copyright 2015, 2017-2019 Albert Astals Cid <aacid at kde.org>
// Copyright 2016 Markus Kilås <digital at markuspage.com>
-// Copyright 2017 Hans-Ulrich Jüttner <huj at froreich-bioscientia.de>
-// Copyright 2017 Adrian Johnson <ajohnson at redneon.com>
+// Copyright 2017, 2019 Hans-Ulrich Jüttner <huj at froreich-bioscientia.de>
+// Copyright 2017, 2019 Adrian Johnson <ajohnson at redneon.com>
// Copyright 2018 Chinmoy Ranjan Pradhan <chinmoyrp65 at protonmail.com>
// Copyright 2019 Alexey Pavlov <alexpux at gmail.com>
//
@@ -33,6 +33,7 @@
#include "PDFDocFactory.h"
#include "Error.h"
#include "GlobalParams.h"
+#include "SignatureHandler.h"
#include "SignatureInfo.h"
#include "Win32Console.h"
#include "numberofcharacters.h"
@@ -118,12 +119,15 @@ static void dumpSignature(int sig_num, int sigCount, FormWidgetSignature *sig_wi
delete path;
}
+static GooString nssDir;
static bool printVersion = false;
static bool printHelp = false;
static bool dontVerifyCert = false;
static bool dumpSignatures = false;
static const ArgDesc argDesc[] = {
+ {"-nssdir", argGooString, &nssDir, 0,
+ "path to directory of libnss3 database"},
{"-nocert", argFlag, &dontVerifyCert, 0,
"don't perform certificate validation"},
{"-dump", argFlag, &dumpSignatures, 0,
@@ -171,6 +175,8 @@ int main(int argc, char *argv[])
fileName = new GooString(argv[argc - 1]);
+ SignatureHandler::setNSSDir(nssDir);
+
// open PDF file
doc = PDFDocFactory().createPDFDoc(*fileName, nullptr, nullptr);
More information about the poppler
mailing list