summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMiklos Vajna <vmiklos@collabora.co.uk>2016-11-17 12:40:06 +0100
committerMiklos Vajna <vmiklos@collabora.co.uk>2016-11-17 15:54:06 +0100
commit972c1e9e7239ef84611b01dad5b112af8f353d3c (patch)
tree6c14d93b01a0071d29da179dc0706ebe36fca876
parent07d4f5d9e3b40025aaee12bb309317b2d267fbdc (diff)
xmlsecurity PDF sign: handle AdES when writing SubFilter
Page 21 of "PAdES baseline signatures" specification from <http://www.etsi.org/deliver/etsi_en/319100_319199/31914201/01.01.01_60/en_31914201v010101p.pdf> says: "The Signature Dictionary shall contain a value of ETSI.CAdES.detached for the key SubFilter." So in case the UI has the adescompliant checkbox enabled, write that value instead of the Adobe default. Change-Id: I69e606a32fb09bebd5e9b25b32150d1b8672f544
-rw-r--r--xmlsecurity/inc/documentsignaturemanager.hxx2
-rw-r--r--xmlsecurity/inc/pdfio/pdfdocument.hxx4
-rw-r--r--xmlsecurity/inc/pdfsignaturehelper.hxx2
-rw-r--r--xmlsecurity/qa/unit/pdfsigning/pdfsigning.cxx2
-rw-r--r--xmlsecurity/source/helper/documentsignaturemanager.cxx10
-rw-r--r--xmlsecurity/source/helper/pdfsignaturehelper.cxx4
-rw-r--r--xmlsecurity/source/pdfio/pdfdocument.cxx14
-rw-r--r--xmlsecurity/source/pdfio/pdfverify.cxx2
8 files changed, 22 insertions, 18 deletions
diff --git a/xmlsecurity/inc/documentsignaturemanager.hxx b/xmlsecurity/inc/documentsignaturemanager.hxx
index 08bdcf62e116..fe9f9a405d38 100644
--- a/xmlsecurity/inc/documentsignaturemanager.hxx
+++ b/xmlsecurity/inc/documentsignaturemanager.hxx
@@ -59,7 +59,7 @@ public:
bool isXML(const OUString& rURI);
SignatureStreamHelper ImplOpenSignatureStream(sal_Int32 eStreamMode, bool bTempStream);
/// Add a new signature, using xCert as a signing certificate, and rDescription as description.
- bool add(const css::uno::Reference<css::security::XCertificate>& xCert, const OUString& rDescription, sal_Int32& nSecurityId, bool bXAdESCompliantIfODF);
+ bool add(const css::uno::Reference<css::security::XCertificate>& xCert, const OUString& rDescription, sal_Int32& nSecurityId, bool bAdESCompliant);
/// Remove signature at nPosition.
void remove(sal_uInt16 nPosition);
/// Read signatures from either a temp stream or the real storage.
diff --git a/xmlsecurity/inc/pdfio/pdfdocument.hxx b/xmlsecurity/inc/pdfio/pdfdocument.hxx
index c282ea694532..31a0546deb38 100644
--- a/xmlsecurity/inc/pdfio/pdfdocument.hxx
+++ b/xmlsecurity/inc/pdfio/pdfdocument.hxx
@@ -117,7 +117,7 @@ class XMLSECURITY_DLLPUBLIC PDFDocument
/// Suggest a minimal, yet free signature ID to use for the next signature.
sal_uInt32 GetNextSignature();
/// Write the signature object as part of signing.
- sal_Int32 WriteSignatureObject(const OUString& rDescription, sal_uInt64& rLastByteRangeOffset, sal_Int64& rSignatureContentOffset);
+ sal_Int32 WriteSignatureObject(const OUString& rDescription, bool bAdES, sal_uInt64& rLastByteRangeOffset, sal_Int64& rSignatureContentOffset);
/// Write the appearance object as part of signing.
sal_Int32 WriteAppearanceObject();
/// Write the annot object as part of signing.
@@ -162,7 +162,7 @@ public:
/// Read elements from the start of the stream till its end.
bool Read(SvStream& rStream);
/// Sign the read document with xCertificate in the edit buffer.
- bool Sign(const css::uno::Reference<css::security::XCertificate>& xCertificate, const OUString& rDescription);
+ bool Sign(const css::uno::Reference<css::security::XCertificate>& xCertificate, const OUString& rDescription, bool bAdES);
/// Serializes the contents of the edit buffer.
bool Write(SvStream& rStream);
/// Get a list of signatures embedded into this document.
diff --git a/xmlsecurity/inc/pdfsignaturehelper.hxx b/xmlsecurity/inc/pdfsignaturehelper.hxx
index 55d8567cf8e9..7efdbfba421f 100644
--- a/xmlsecurity/inc/pdfsignaturehelper.hxx
+++ b/xmlsecurity/inc/pdfsignaturehelper.hxx
@@ -43,7 +43,7 @@ public:
/// Comment / reason to be used next time signing is performed.
void SetDescription(const OUString& rDescription);
/// Append a new signature at the end of xInputStream.
- bool Sign(const css::uno::Reference<css::io::XInputStream>& xInputStream);
+ bool Sign(const css::uno::Reference<css::io::XInputStream>& xInputStream, bool bAdES);
/// Remove the signature at nPosition (and all dependent signatures) from xInputStream.
static bool RemoveSignature(const css::uno::Reference<css::io::XInputStream>& xInputStream, sal_uInt16 nPosition);
};
diff --git a/xmlsecurity/qa/unit/pdfsigning/pdfsigning.cxx b/xmlsecurity/qa/unit/pdfsigning/pdfsigning.cxx
index d052e5f451dc..99e176b03b07 100644
--- a/xmlsecurity/qa/unit/pdfsigning/pdfsigning.cxx
+++ b/xmlsecurity/qa/unit/pdfsigning/pdfsigning.cxx
@@ -142,7 +142,7 @@ bool PDFSigningTest::sign(const OUString& rInURL, const OUString& rOutURL, size_
// NSS failed to parse it's own profile or Windows has no certificates installed.
return false;
}
- CPPUNIT_ASSERT(aDocument.Sign(aCertificates[0], "test"));
+ CPPUNIT_ASSERT(aDocument.Sign(aCertificates[0], "test", /*bAdES=*/true));
SvFileStream aOutStream(rOutURL, StreamMode::WRITE | StreamMode::TRUNC);
CPPUNIT_ASSERT(aDocument.Write(aOutStream));
}
diff --git a/xmlsecurity/source/helper/documentsignaturemanager.cxx b/xmlsecurity/source/helper/documentsignaturemanager.cxx
index f9b435502e6b..76e0b0aefaa9 100644
--- a/xmlsecurity/source/helper/documentsignaturemanager.cxx
+++ b/xmlsecurity/source/helper/documentsignaturemanager.cxx
@@ -232,7 +232,7 @@ SignatureStreamHelper DocumentSignatureManager::ImplOpenSignatureStream(sal_Int3
return aHelper;
}
-bool DocumentSignatureManager::add(const uno::Reference<security::XCertificate>& xCert, const OUString& rDescription, sal_Int32& nSecurityId, bool bXAdESCompliantIfODF)
+bool DocumentSignatureManager::add(const uno::Reference<security::XCertificate>& xCert, const OUString& rDescription, sal_Int32& nSecurityId, bool bAdESCompliant)
{
if (!xCert.is())
{
@@ -255,7 +255,7 @@ bool DocumentSignatureManager::add(const uno::Reference<security::XCertificate>&
getPDFSignatureHelper().SetX509Certificate(xCert);
getPDFSignatureHelper().SetDescription(rDescription);
uno::Reference<io::XInputStream> xInputStream(mxSignatureStream, uno::UNO_QUERY);
- if (!getPDFSignatureHelper().Sign(xInputStream))
+ if (!getPDFSignatureHelper().Sign(xInputStream, bAdESCompliant))
{
SAL_WARN("xmlsecurity.helper", "PDFSignatureHelper::Sign() failed");
return false;
@@ -299,7 +299,7 @@ bool DocumentSignatureManager::add(const uno::Reference<security::XCertificate>&
for (sal_Int32 n = 0; n < nElements; n++)
{
bool bBinaryMode = !isXML(aElements[n]);
- maSignatureHelper.AddForSigning(nSecurityId, aElements[n], aElements[n], bBinaryMode, bXAdESCompliantIfODF);
+ maSignatureHelper.AddForSigning(nSecurityId, aElements[n], aElements[n], bBinaryMode, bAdESCompliant);
}
maSignatureHelper.SetDateTime(nSecurityId, Date(Date::SYSTEM), tools::Time(tools::Time::SYSTEM));
@@ -321,10 +321,10 @@ bool DocumentSignatureManager::add(const uno::Reference<security::XCertificate>&
uno::Reference<xml::sax::XDocumentHandler> xDocumentHandler(xSaxWriter, uno::UNO_QUERY_THROW);
std::size_t nInfos = maCurrentSignatureInformations.size();
for (std::size_t n = 0; n < nInfos; n++)
- XMLSignatureHelper::ExportSignature(xDocumentHandler, maCurrentSignatureInformations[n], bXAdESCompliantIfODF);
+ XMLSignatureHelper::ExportSignature(xDocumentHandler, maCurrentSignatureInformations[n], bAdESCompliant);
// Create a new one...
- maSignatureHelper.CreateAndWriteSignature(xDocumentHandler, bXAdESCompliantIfODF);
+ maSignatureHelper.CreateAndWriteSignature(xDocumentHandler, bAdESCompliant);
// That's it...
XMLSignatureHelper::CloseDocumentHandler(xDocumentHandler);
diff --git a/xmlsecurity/source/helper/pdfsignaturehelper.cxx b/xmlsecurity/source/helper/pdfsignaturehelper.cxx
index ff79af8ca730..a7cfbed66e72 100644
--- a/xmlsecurity/source/helper/pdfsignaturehelper.cxx
+++ b/xmlsecurity/source/helper/pdfsignaturehelper.cxx
@@ -118,7 +118,7 @@ void PDFSignatureHelper::SetDescription(const OUString& rDescription)
m_aDescription = rDescription;
}
-bool PDFSignatureHelper::Sign(const uno::Reference<io::XInputStream>& xInputStream)
+bool PDFSignatureHelper::Sign(const uno::Reference<io::XInputStream>& xInputStream, bool bAdES)
{
std::unique_ptr<SvStream> pStream(utl::UcbStreamHelper::CreateStream(xInputStream, true));
xmlsecurity::pdfio::PDFDocument aDocument;
@@ -128,7 +128,7 @@ bool PDFSignatureHelper::Sign(const uno::Reference<io::XInputStream>& xInputStre
return false;
}
- if (!aDocument.Sign(m_xCertificate, m_aDescription))
+ if (!aDocument.Sign(m_xCertificate, m_aDescription, bAdES))
{
SAL_WARN("xmlsecurity.helper", "failed to sign");
return false;
diff --git a/xmlsecurity/source/pdfio/pdfdocument.cxx b/xmlsecurity/source/pdfio/pdfdocument.cxx
index 0d5aec0ca1f2..9c71451601c4 100644
--- a/xmlsecurity/source/pdfio/pdfdocument.cxx
+++ b/xmlsecurity/source/pdfio/pdfdocument.cxx
@@ -357,7 +357,7 @@ sal_uInt32 PDFDocument::GetNextSignature()
return nRet + 1;
}
-sal_Int32 PDFDocument::WriteSignatureObject(const OUString& rDescription, sal_uInt64& rLastByteRangeOffset, sal_Int64& rContentOffset)
+sal_Int32 PDFDocument::WriteSignatureObject(const OUString& rDescription, bool bAdES, sal_uInt64& rLastByteRangeOffset, sal_Int64& rContentOffset)
{
// Write signature object.
sal_Int32 nSignatureId = m_aXRef.size();
@@ -374,7 +374,11 @@ sal_Int32 PDFDocument::WriteSignatureObject(const OUString& rDescription, sal_uI
OStringBuffer aContentFiller(MAX_SIGNATURE_CONTENT_LENGTH);
comphelper::string::padToLength(aContentFiller, MAX_SIGNATURE_CONTENT_LENGTH, '0');
aSigBuffer.append(aContentFiller.makeStringAndClear());
- aSigBuffer.append(">\n/Type/Sig/SubFilter/adbe.pkcs7.detached");
+ aSigBuffer.append(">\n/Type/Sig/SubFilter");
+ if (bAdES)
+ aSigBuffer.append("/ETSI.CAdES.detached");
+ else
+ aSigBuffer.append("/adbe.pkcs7.detached");
// Time of signing.
aSigBuffer.append(" /M (");
@@ -941,14 +945,14 @@ void PDFDocument::WriteXRef(sal_uInt64 nXRefOffset, PDFReferenceElement* pRoot)
}
}
-bool PDFDocument::Sign(const uno::Reference<security::XCertificate>& xCertificate, const OUString& rDescription)
+bool PDFDocument::Sign(const uno::Reference<security::XCertificate>& xCertificate, const OUString& rDescription, bool bAdES)
{
m_aEditBuffer.Seek(STREAM_SEEK_TO_END);
m_aEditBuffer.WriteCharPtr("\n");
sal_uInt64 nSignatureLastByteRangeOffset = 0;
sal_Int64 nSignatureContentOffset = 0;
- sal_Int32 nSignatureId = WriteSignatureObject(rDescription, nSignatureLastByteRangeOffset, nSignatureContentOffset);
+ sal_Int32 nSignatureId = WriteSignatureObject(rDescription, bAdES, nSignatureLastByteRangeOffset, nSignatureContentOffset);
sal_Int32 nAppearanceId = WriteAppearanceObject();
@@ -2021,7 +2025,7 @@ bool PDFDocument::ValidateSignature(SvStream& rStream, PDFObjectElement* pSignat
}
auto pSubFilter = dynamic_cast<PDFNameElement*>(pValue->Lookup("SubFilter"));
- if (!pSubFilter || pSubFilter->GetValue() != "adbe.pkcs7.detached")
+ if (!pSubFilter || (pSubFilter->GetValue() != "adbe.pkcs7.detached" && pSubFilter->GetValue() != "ETSI.CAdES.detached"))
{
SAL_WARN("xmlsecurity.pdfio", "PDFDocument::ValidateSignature: no or unsupported sub-filter");
return false;
diff --git a/xmlsecurity/source/pdfio/pdfverify.cxx b/xmlsecurity/source/pdfio/pdfverify.cxx
index b288067c080d..04c33d8fc139 100644
--- a/xmlsecurity/source/pdfio/pdfverify.cxx
+++ b/xmlsecurity/source/pdfio/pdfverify.cxx
@@ -136,7 +136,7 @@ SAL_IMPLEMENT_MAIN_WITH_ARGS(nArgc, pArgv)
SAL_WARN("xmlsecurity.pdfio", "no signing certificates found");
return 1;
}
- if (!aDocument.Sign(aCertificates[0], "pdfverify"))
+ if (!aDocument.Sign(aCertificates[0], "pdfverify", /*bAdES=*/true))
{
SAL_WARN("xmlsecurity.pdfio", "failed to sign");
return 1;