Kaydet (Commit) 57e6b9f3 authored tarafından Miklos Vajna's avatar Miklos Vajna

xmlsecurity OOXML export: remove signature relation with the last signature

The signature relation refers to _xmlsignatures/origin.sigs, but
that's not written when all signatures are removed.

Change-Id: I5ee1c8849962cba4b338e6f43243bcf89aedad36
üst 64f86c7f
......@@ -181,8 +181,8 @@ public:
bool ReadAndVerifySignatureStorage(const css::uno::Reference<css::embed::XStorage>& xStorage, bool bCacheLastSignature = true);
/// Read and verify a single OOXML signature.
bool ReadAndVerifySignatureStorageStream(const css::uno::Reference<css::io::XInputStream>& xInputStream);
/// Adds an OOXML digital signature relation to _rels/.rels if there wasn't any before.
void EnsureSignaturesRelation(css::uno::Reference<css::embed::XStorage> xStorage);
/// Adds or removes an OOXML digital signature relation to _rels/.rels if there wasn't any before.
void EnsureSignaturesRelation(css::uno::Reference<css::embed::XStorage> xStorage, bool bAdd);
/// Given that xStorage is an OOXML _xmlsignatures storage, create origin.sigs and its relations.
void ExportSignatureRelations(css::uno::Reference<css::embed::XStorage> xStorage, int nSignatureCount);
/// Given that xSignatureStorage is an OOXML _xmlsignatures storage, create and write a new signature.
......
......@@ -264,7 +264,7 @@ bool DocumentSignatureManager::add(const uno::Reference<security::XCertificate>&
// OOXML
// Handle relations.
maSignatureHelper.EnsureSignaturesRelation(mxStore);
maSignatureHelper.EnsureSignaturesRelation(mxStore, /*bAdd=*/true);
// Old signatures + the new one.
int nSignatureCount = maCurrentSignatureInformations.size() + 1;
maSignatureHelper.ExportSignatureRelations(aStreamHelper.xSignatureStorage, nSignatureCount);
......@@ -379,6 +379,11 @@ void DocumentSignatureManager::write()
maSignatureHelper.ExportSignatureContentTypes(mxStore, nSignatureCount);
maSignatureHelper.ExportSignatureRelations(aStreamHelper.xSignatureStorage, nSignatureCount);
}
else
{
// Removing all signatures: then need to remove the signature relation as well.
maSignatureHelper.EnsureSignaturesRelation(mxStore, /*bAdd=*/false);
}
for (size_t i = 0; i < nSignatureCount; ++i)
maSignatureHelper.ExportOOXMLSignature(mxStore, aStreamHelper.xSignatureStorage, maCurrentSignatureInformations[i], i + 1);
......
......@@ -487,7 +487,7 @@ bool XMLSignatureHelper::ReadAndVerifySignatureStorageStream(const css::uno::Ref
return !mbError;
}
void XMLSignatureHelper::EnsureSignaturesRelation(css::uno::Reference<css::embed::XStorage> xStorage)
void XMLSignatureHelper::EnsureSignaturesRelation(css::uno::Reference<css::embed::XStorage> xStorage, bool bAdd)
{
sal_Int32 nOpenMode = embed::ElementModes::READWRITE;
uno::Reference<embed::XStorage> xSubStorage = xStorage->openStorageElement("_rels", nOpenMode);
......@@ -496,21 +496,40 @@ void XMLSignatureHelper::EnsureSignaturesRelation(css::uno::Reference<css::embed
aRelationsInfo = comphelper::sequenceToContainer< std::vector< uno::Sequence<beans::StringPair> > >(comphelper::OFOPXMLHelper::ReadRelationsInfoSequence(xRelStream, ".rels", mxCtx));
// Do we have a relation already?
bool bHaveRelation = false;
int nCount = 0;
for (const uno::Sequence<beans::StringPair>& rRelation : aRelationsInfo)
{
auto aRelation = comphelper::sequenceToContainer< std::vector<beans::StringPair> >(rRelation);
if (std::find_if(aRelation.begin(), aRelation.end(), lcl_isSignatureOriginType) != aRelation.end())
return;
{
bHaveRelation = true;
break;
}
++nCount;
}
// No, then add one.
std::vector<beans::StringPair> aRelation;
aRelation.push_back(beans::StringPair("Id", "rId" + OUString::number(++nCount)));
aRelation.push_back(beans::StringPair("Type", OOXML_SIGNATURE_ORIGIN));
aRelation.push_back(beans::StringPair("Target", "_xmlsignatures/origin.sigs"));
aRelationsInfo.push_back(comphelper::containerToSequence(aRelation));
if (!bHaveRelation && bAdd)
{
// No, and have to add one.
std::vector<beans::StringPair> aRelation;
aRelation.push_back(beans::StringPair("Id", "rId" + OUString::number(++nCount)));
aRelation.push_back(beans::StringPair("Type", OOXML_SIGNATURE_ORIGIN));
aRelation.push_back(beans::StringPair("Target", "_xmlsignatures/origin.sigs"));
aRelationsInfo.push_back(comphelper::containerToSequence(aRelation));
}
else if (bHaveRelation && !bAdd)
{
// Yes, and need to remove it.
for (std::vector< uno::Sequence<beans::StringPair> >::iterator it = aRelationsInfo.begin(); it != aRelationsInfo.end();)
{
auto aRelation = comphelper::sequenceToContainer< std::vector<beans::StringPair> >(*it);
if (std::find_if(aRelation.begin(), aRelation.end(), lcl_isSignatureOriginType) != aRelation.end())
it = aRelationsInfo.erase(it);
else
++it;
}
}
// Write it back.
uno::Reference<io::XTruncate> xTruncate(xRelStream, uno::UNO_QUERY);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment