diff options
author | Christian Mollekopf <chrigi_1@fastmail.fm> | 2018-04-25 09:21:56 +0200 |
---|---|---|
committer | Christian Mollekopf <chrigi_1@fastmail.fm> | 2018-04-25 10:24:22 +0200 |
commit | 595930d82b38a567dc6f0d699276b715b09fa109 (patch) | |
tree | 533778c77c5398d94ab9d4fd5dc03b51cbdd8700 /framework/src/domain/mime/mimetreeparser | |
parent | a9c6bf7b55358a658f2ab8886ce5b5509ef518dc (diff) | |
download | kube-595930d82b38a567dc6f0d699276b715b09fa109.tar.gz kube-595930d82b38a567dc6f0d699276b715b09fa109.zip |
Fixed the case where we have plaintext inside the encrypted part.
This is triggered when we have encrypted+signed inline parts.
Diffstat (limited to 'framework/src/domain/mime/mimetreeparser')
3 files changed, 42 insertions, 19 deletions
diff --git a/framework/src/domain/mime/mimetreeparser/messagepart.cpp b/framework/src/domain/mime/mimetreeparser/messagepart.cpp index 17719ff8..9b677d86 100644 --- a/framework/src/domain/mime/mimetreeparser/messagepart.cpp +++ b/framework/src/domain/mime/mimetreeparser/messagepart.cpp | |||
@@ -261,6 +261,28 @@ void MessagePart::parseInternal(KMime::Content *node, bool onlyOneMimePart) | |||
261 | } | 261 | } |
262 | } | 262 | } |
263 | 263 | ||
264 | void MessagePart::parseInternal(const QByteArray &data) | ||
265 | { | ||
266 | auto tempNode = new KMime::Content(); | ||
267 | |||
268 | const auto lfData = KMime::CRLFtoLF(data); | ||
269 | //We have to deal with both bodies and full parts. In inline encrypted/signed parts we can have nested parts, | ||
270 | //or just plain-text, and both ends up here. setContent defaults to setting only the header, so we have to avoid this. | ||
271 | if (lfData.contains("\n\n")) { | ||
272 | tempNode->setContent(lfData); | ||
273 | } else { | ||
274 | tempNode->setBody(lfData); | ||
275 | } | ||
276 | tempNode->parse(); | ||
277 | bindLifetime(tempNode); | ||
278 | |||
279 | if (!tempNode->head().isEmpty()) { | ||
280 | tempNode->contentDescription()->from7BitString("temporary node"); | ||
281 | } | ||
282 | |||
283 | parseInternal(tempNode, false); | ||
284 | } | ||
285 | |||
264 | QString MessagePart::renderInternalText() const | 286 | QString MessagePart::renderInternalText() const |
265 | { | 287 | { |
266 | QString text; | 288 | QString text; |
@@ -392,7 +414,8 @@ void TextMessagePart::parseContent() | |||
392 | const QString &fromAddress = mOtp->nodeHelper()->fromAsString(mNode); | 414 | const QString &fromAddress = mOtp->nodeHelper()->fromAsString(mNode); |
393 | mSignatureState = KMMsgNotSigned; | 415 | mSignatureState = KMMsgNotSigned; |
394 | mEncryptionState = KMMsgNotEncrypted; | 416 | mEncryptionState = KMMsgNotEncrypted; |
395 | const auto blocks = prepareMessageForDecryption(mNode->decodedContent()); | 417 | auto body = mNode->decodedContent(); |
418 | const auto blocks = prepareMessageForDecryption(body); | ||
396 | 419 | ||
397 | const auto cryptProto = GpgME::OpenPGP; | 420 | const auto cryptProto = GpgME::OpenPGP; |
398 | 421 | ||
@@ -880,15 +903,8 @@ void SignedMessagePart::setVerificationResult(const GpgME::VerificationResult &r | |||
880 | mOtp->mNodeHelper->setPartMetaData(mNode, mMetaData); | 903 | mOtp->mNodeHelper->setPartMetaData(mNode, mMetaData); |
881 | } | 904 | } |
882 | if (!plainText.isEmpty() && parseText) { | 905 | if (!plainText.isEmpty() && parseText) { |
883 | auto tempNode = new KMime::Content(); | 906 | parseInternal(plainText); |
884 | tempNode->setBody(plainText); | ||
885 | tempNode->parse(); | ||
886 | bindLifetime(tempNode); | ||
887 | 907 | ||
888 | if (!tempNode->head().isEmpty()) { | ||
889 | tempNode->contentDescription()->from7BitString("signed data"); | ||
890 | } | ||
891 | parseInternal(tempNode, false); | ||
892 | } | 908 | } |
893 | } | 909 | } |
894 | } | 910 | } |
@@ -1072,16 +1088,7 @@ void EncryptedMessagePart::startDecryption(KMime::Content *data) | |||
1072 | 1088 | ||
1073 | if (mNode && !mMetaData.isSigned) { | 1089 | if (mNode && !mMetaData.isSigned) { |
1074 | mOtp->mNodeHelper->setPartMetaData(mNode, mMetaData); | 1090 | mOtp->mNodeHelper->setPartMetaData(mNode, mMetaData); |
1075 | auto tempNode = new KMime::Content(); | 1091 | parseInternal(mDecryptedData); |
1076 | tempNode->setContent(KMime::CRLFtoLF(mDecryptedData.constData())); | ||
1077 | tempNode->parse(); | ||
1078 | bindLifetime(tempNode); | ||
1079 | |||
1080 | if (!tempNode->head().isEmpty()) { | ||
1081 | tempNode->contentDescription()->from7BitString("encrypted data"); | ||
1082 | } | ||
1083 | |||
1084 | parseInternal(tempNode, false); | ||
1085 | } | 1092 | } |
1086 | } | 1093 | } |
1087 | 1094 | ||
diff --git a/framework/src/domain/mime/mimetreeparser/messagepart.h b/framework/src/domain/mime/mimetreeparser/messagepart.h index c039637a..8cd74717 100644 --- a/framework/src/domain/mime/mimetreeparser/messagepart.h +++ b/framework/src/domain/mime/mimetreeparser/messagepart.h | |||
@@ -125,6 +125,7 @@ public: | |||
125 | 125 | ||
126 | protected: | 126 | protected: |
127 | void parseInternal(KMime::Content *node, bool onlyOneMimePart); | 127 | void parseInternal(KMime::Content *node, bool onlyOneMimePart); |
128 | void parseInternal(const QByteArray &data); | ||
128 | QString renderInternalText() const; | 129 | QString renderInternalText() const; |
129 | 130 | ||
130 | QString mText; | 131 | QString mText; |
diff --git a/framework/src/domain/mime/mimetreeparser/tests/mimetreeparsertest.cpp b/framework/src/domain/mime/mimetreeparser/tests/mimetreeparsertest.cpp index 90a07a7c..38857d58 100644 --- a/framework/src/domain/mime/mimetreeparser/tests/mimetreeparsertest.cpp +++ b/framework/src/domain/mime/mimetreeparser/tests/mimetreeparsertest.cpp | |||
@@ -386,6 +386,21 @@ private slots: | |||
386 | QCOMPARE(part->encryptionState(), MimeTreeParser::KMMsgFullyEncrypted); | 386 | QCOMPARE(part->encryptionState(), MimeTreeParser::KMMsgFullyEncrypted); |
387 | QCOMPARE(otp.plainTextContent(), QString::fromUtf8("sdflskjsdf\n\n-- \nThis is a HTML signature.\n")); | 387 | QCOMPARE(otp.plainTextContent(), QString::fromUtf8("sdflskjsdf\n\n-- \nThis is a HTML signature.\n")); |
388 | } | 388 | } |
389 | |||
390 | void testOpenpgpMultipartEmbeddedSigned() | ||
391 | { | ||
392 | MimeTreeParser::ObjectTreeParser otp; | ||
393 | otp.parseObjectTree(readMailFromFile("openpgp-multipart-embedded-signed.mbox")); | ||
394 | otp.decryptParts(); | ||
395 | auto partList = otp.collectContentParts(); | ||
396 | QCOMPARE(partList.size(), 1); | ||
397 | auto part = partList[0].dynamicCast<MimeTreeParser::MessagePart>(); | ||
398 | QCOMPARE(part->encryptions().size(), 1); | ||
399 | QCOMPARE(part->signatures().size(), 1); | ||
400 | QCOMPARE(part->encryptionState(), MimeTreeParser::KMMsgFullyEncrypted); | ||
401 | QCOMPARE(part->signatureState(), MimeTreeParser::KMMsgFullySigned); | ||
402 | QCOMPARE(otp.plainTextContent(), QString::fromUtf8("test\n\n-- \nThis is a HTML signature.\n")); | ||
403 | } | ||
389 | }; | 404 | }; |
390 | 405 | ||
391 | QTEST_GUILESS_MAIN(InterfaceTest) | 406 | QTEST_GUILESS_MAIN(InterfaceTest) |