1 /* -------------------------------------------------------------------- 2 * Filename: 3 * src/parsers/mime/mime.h 4 * 5 * Description: 6 * Declaration of main mime parser components 7 * -------------------------------------------------------------------- 8 * Copyright 2002-2005 Andreas Aardal Hanssen 9 * 10 * This program is free software; you can redistribute it and/or modify 11 * it under the terms of the GNU General Public License as published by 12 * the Free Software Foundation; either version 2 of the License, or 13 * (at your option) any later version. 14 * 15 * This program is distributed in the hope that it will be useful, 16 * but WITHOUT ANY WARRANTY; without even the implied warranty of 17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18 * GNU General Public License for more details. 19 * 20 * You should have received a copy of the GNU General Public License 21 * along with this program; if not, write to the Free Software 22 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. 23 * -------------------------------------------------------------------- 24 */ 25 #ifndef mime_h_included 26 #define mime_h_included 27 28 #include <string> 29 #include <vector> 30 #include <map> 31 #include <stdio.h> 32 33 namespace Binc { 34 35 class MimeInputSource; 36 37 38 //---------------------------------------------------------------------- 39 class HeaderItem { 40 private: 41 mutable std::string key; 42 mutable std::string value; 43 44 public: getKey(void)45 inline const std::string &getKey(void) const { return key; } getValue(void)46 inline const std::string &getValue(void) const { return value; } 47 48 //-- 49 HeaderItem(void); 50 HeaderItem(const std::string &key, const std::string &value); 51 }; 52 53 //---------------------------------------------------------------------- 54 class Header { 55 private: 56 mutable std::vector<HeaderItem> content; 57 58 public: 59 bool getFirstHeader(const std::string &key, HeaderItem &dest) const; 60 bool getAllHeaders(const std::string &key, std::vector<HeaderItem> &dest) 61 const; 62 void add(const std::string &name, const std::string &content); 63 void clear(void); 64 65 //-- 66 Header(void); 67 ~Header(void); 68 }; 69 70 //---------------------------------------------------------------------- 71 class IODevice; 72 class MimeDocument; 73 class MimePart { 74 protected: 75 public: 76 mutable bool multipart; 77 mutable bool messagerfc822; 78 mutable std::string subtype; 79 mutable std::string boundary; 80 81 mutable unsigned int headerstartoffsetcrlf; 82 mutable unsigned int headerlength; 83 84 mutable unsigned int bodystartoffsetcrlf; 85 mutable unsigned int bodylength; 86 mutable unsigned int nlines; 87 mutable unsigned int nbodylines; 88 mutable unsigned int size; 89 90 public: 91 enum FetchType { 92 FetchBody, 93 FetchHeader, 94 FetchMime 95 }; 96 97 mutable Header h; 98 99 mutable std::vector<MimePart> members; 100 getSubType(void)101 inline const std::string &getSubType(void) const { return subtype; } isMultipart(void)102 inline bool isMultipart(void) const { return multipart; } isMessageRFC822(void)103 inline bool isMessageRFC822(void) const { return messagerfc822; } getSize(void)104 inline unsigned int getSize(void) const { return bodylength; } getNofLines(void)105 inline unsigned int getNofLines(void) const { return nlines; } getNofBodyLines(void)106 inline unsigned int getNofBodyLines(void) const { return nbodylines; } getBodyLength(void)107 inline unsigned int getBodyLength(void) const { return bodylength; } getBodyStartOffset(void)108 inline unsigned int getBodyStartOffset(void) const { 109 return bodystartoffsetcrlf; } 110 111 void printBody(Binc::IODevice &output, unsigned int startoffset, 112 unsigned int length) const; 113 void getBody(std::string& s, unsigned int startoffset, unsigned int length) 114 const; 115 virtual void clear(void); 116 117 virtual int doParseOnlyHeader(MimeInputSource *ms); 118 virtual int doParseFull(MimeInputSource *ms, 119 const std::string &toboundary, int &boundarysize); 120 121 MimePart(void); 122 virtual ~MimePart(void); 123 124 private: 125 MimeInputSource *mimeSource; 126 127 bool parseOneHeaderLine(Binc::Header *header, unsigned int *nlines); 128 129 bool skipUntilBoundary(const std::string &delimiter, 130 unsigned int *nlines, bool *eof); 131 inline void postBoundaryProcessing(bool *eof, 132 unsigned int *nlines, 133 int *boundarysize, 134 bool *foundendofpart); 135 void parseMultipart(const std::string &boundary, 136 const std::string &toboundary, 137 bool *eof, 138 unsigned int *nlines, 139 int *boundarysize, 140 bool *foundendofpart, 141 unsigned int *bodylength, 142 std::vector<Binc::MimePart> *members); 143 void parseSinglePart(const std::string &toboundary, 144 int *boundarysize, 145 unsigned int *nbodylines, 146 unsigned int *nlines, 147 bool *eof, bool *foundendofpart, 148 unsigned int *bodylength); 149 void parseHeader(Binc::Header *header, unsigned int *nlines); 150 void analyzeHeader(Binc::Header *header, bool *multipart, 151 bool *messagerfc822, std::string *subtype, 152 std::string *boundary); 153 void parseMessageRFC822(std::vector<Binc::MimePart> *members, 154 bool *foundendofpart, 155 unsigned int *bodylength, 156 unsigned int *nbodylines, 157 const std::string &toboundary); 158 }; 159 160 //---------------------------------------------------------------------- 161 class MimeDocument : public MimePart { 162 public: 163 MimeDocument(void); 164 ~MimeDocument(void); 165 166 void parseOnlyHeader(int fd); 167 void parseFull(int fd); 168 void parseOnlyHeader(std::istream& s); 169 void parseFull(std::istream& s); 170 171 void clear(void); 172 isHeaderParsed(void)173 bool isHeaderParsed(void) const { 174 return headerIsParsed; 175 } isAllParsed(void)176 bool isAllParsed(void) const { 177 return allIsParsed; 178 } 179 180 private: 181 bool headerIsParsed; 182 bool allIsParsed; 183 MimeInputSource *doc_mimeSource; 184 }; 185 186 }; 187 188 #endif 189