diff options
author | Christian Mollekopf <chrigi_1@fastmail.fm> | 2017-10-26 13:05:04 +0200 |
---|---|---|
committer | Christian Mollekopf <chrigi_1@fastmail.fm> | 2017-10-26 13:05:04 +0200 |
commit | ecbd3b67e3f6e2bd3025b1fb9c734335612e554e (patch) | |
tree | f20b20dca3b6621834c167b870ac453f3bf9afc1 /common | |
parent | 6db02b1f5b3d47578e1bc0a9bb7ca85da2fe2de8 (diff) | |
download | sink-ecbd3b67e3f6e2bd3025b1fb9c734335612e554e.tar.gz sink-ecbd3b67e3f6e2bd3025b1fb9c734335612e554e.zip |
Fixed parsing of larger headers.
Just truncating the file is not a good idea. If the headers end up being
larger (I just ran into that), then we just fail to parse the headers
and miss important stuff like subjects. So let's not.
Diffstat (limited to 'common')
-rw-r--r-- | common/mailpreprocessor.cpp | 33 |
1 files changed, 21 insertions, 12 deletions
diff --git a/common/mailpreprocessor.cpp b/common/mailpreprocessor.cpp index 253e8b4..b1cb1d5 100644 --- a/common/mailpreprocessor.cpp +++ b/common/mailpreprocessor.cpp | |||
@@ -37,8 +37,7 @@ QString MailPropertyExtractor::getFilePathFromMimeMessagePath(const QString &s) | |||
37 | struct MimeMessageReader { | 37 | struct MimeMessageReader { |
38 | MimeMessageReader(const QString &mimeMessagePath) | 38 | MimeMessageReader(const QString &mimeMessagePath) |
39 | : f(mimeMessagePath), | 39 | : f(mimeMessagePath), |
40 | mapped(0), | 40 | mapped(0) |
41 | mappedSize(0) | ||
42 | { | 41 | { |
43 | if (mimeMessagePath.isNull()) { | 42 | if (mimeMessagePath.isNull()) { |
44 | SinkTrace() << "No mime message"; | 43 | SinkTrace() << "No mime message"; |
@@ -53,8 +52,7 @@ struct MimeMessageReader { | |||
53 | SinkWarning() << "The file is empty."; | 52 | SinkWarning() << "The file is empty."; |
54 | return; | 53 | return; |
55 | } | 54 | } |
56 | mappedSize = qMin((qint64)8000, f.size()); | 55 | mapped = f.map(0, f.size()); |
57 | mapped = f.map(0, mappedSize); | ||
58 | if (!mapped) { | 56 | if (!mapped) { |
59 | SinkWarning() << "Failed to map the file: " << f.errorString(); | 57 | SinkWarning() << "Failed to map the file: " << f.errorString(); |
60 | return; | 58 | return; |
@@ -64,19 +62,30 @@ struct MimeMessageReader { | |||
64 | KMime::Message::Ptr mimeMessage() | 62 | KMime::Message::Ptr mimeMessage() |
65 | { | 63 | { |
66 | if (!mapped) { | 64 | if (!mapped) { |
67 | return KMime::Message::Ptr(); | 65 | return {}; |
68 | } | 66 | } |
69 | Q_ASSERT(mapped); | 67 | QByteArray result; |
70 | Q_ASSERT(mappedSize); | 68 | //Seek for end of headers |
71 | auto msg = KMime::Message::Ptr(new KMime::Message); | 69 | const auto content = QByteArray::fromRawData(reinterpret_cast<const char*>(mapped), f.size()); |
72 | msg->setHead(KMime::CRLFtoLF(QByteArray::fromRawData(reinterpret_cast<const char*>(mapped), mappedSize))); | 70 | int pos = content.indexOf("\r\n\r\n", 0); |
73 | msg->parse(); | 71 | int offset = 2; |
74 | return msg; | 72 | if (pos < 0) { |
73 | pos = content.indexOf("\n\n", 0); | ||
74 | offset = 1; | ||
75 | } | ||
76 | if (pos > -1) { | ||
77 | const auto header = content.left(pos + offset); //header *must* end with "\n" !! | ||
78 | auto msg = KMime::Message::Ptr(new KMime::Message); | ||
79 | msg->setHead(KMime::CRLFtoLF(header)); | ||
80 | msg->parse(); | ||
81 | return msg; | ||
82 | } | ||
83 | SinkWarning() << "Failed to find end of headers" << content; | ||
84 | return {}; | ||
75 | } | 85 | } |
76 | 86 | ||
77 | QFile f; | 87 | QFile f; |
78 | uchar *mapped; | 88 | uchar *mapped; |
79 | qint64 mappedSize; | ||
80 | }; | 89 | }; |
81 | 90 | ||
82 | static Sink::ApplicationDomain::Mail::Contact getContact(const KMime::Headers::Generics::MailboxList *header) | 91 | static Sink::ApplicationDomain::Mail::Contact getContact(const KMime::Headers::Generics::MailboxList *header) |