aboutsummaryrefslogtreecommitdiffstats
path: root/src/utility/encoder/uuEncoder.cpp
diff options
context:
space:
mode:
authorVincent Richard <[email protected]>2013-12-29 09:02:12 +0000
committerVincent Richard <[email protected]>2013-12-29 09:02:12 +0000
commit152c6bed75598a6ca5efb7914701157270155833 (patch)
tree8faced1d75a45c819630323da256248415992ed0 /src/utility/encoder/uuEncoder.cpp
parentMerge branch 'master' of https://github.com/kisli/vmime (diff)
downloadvmime-152c6bed75598a6ca5efb7914701157270155833.tar.gz
vmime-152c6bed75598a6ca5efb7914701157270155833.zip
Merged source and header files in directory structure. Got rid of SConstruct build.
Diffstat (limited to 'src/utility/encoder/uuEncoder.cpp')
-rw-r--r--src/utility/encoder/uuEncoder.cpp344
1 files changed, 0 insertions, 344 deletions
diff --git a/src/utility/encoder/uuEncoder.cpp b/src/utility/encoder/uuEncoder.cpp
deleted file mode 100644
index 0375a397..00000000
--- a/src/utility/encoder/uuEncoder.cpp
+++ /dev/null
@@ -1,344 +0,0 @@
-//
-// VMime library (http://www.vmime.org)
-// Copyright (C) 2002-2013 Vincent Richard <[email protected]>
-//
-// This program is free software; you can redistribute it and/or
-// modify it under the terms of the GNU General Public License as
-// published by the Free Software Foundation; either version 3 of
-// the License, or (at your option) any later version.
-//
-// This program is distributed in the hope that it will be useful,
-// but WITHOUT ANY WARRANTY; without even the implied warranty of
-// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
-// General Public License for more details.
-//
-// You should have received a copy of the GNU General Public License along
-// with this program; if not, write to the Free Software Foundation, Inc.,
-// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
-//
-// Linking this library statically or dynamically with other modules is making
-// a combined work based on this library. Thus, the terms and conditions of
-// the GNU General Public License cover the whole combination.
-//
-
-#include "vmime/utility/encoder/uuEncoder.hpp"
-#include "vmime/parserHelpers.hpp"
-
-
-namespace vmime {
-namespace utility {
-namespace encoder {
-
-
-uuEncoder::uuEncoder()
-{
- getProperties()["mode"] = 644;
- getProperties()["filename"] = "no_name";
- getProperties()["maxlinelength"] = 46;
-}
-
-
-const std::vector <string> uuEncoder::getAvailableProperties() const
-{
- std::vector <string> list(encoder::getAvailableProperties());
-
- list.push_back("maxlinelength");
-
- list.push_back("mode");
- list.push_back("filename");
-
- return (list);
-}
-
-
-// This is the character encoding function to make a character printable
-static inline byte_t UUENCODE(const unsigned int c)
-{
- return static_cast <byte_t>((c & 077) + ' ');
-}
-
-// Single character decoding
-static inline unsigned int UUDECODE(const unsigned int c)
-{
- return (c - ' ') & 077;
-}
-
-
-size_t uuEncoder::encode(utility::inputStream& in,
- utility::outputStream& out, utility::progressListener* progress)
-{
- in.reset(); // may not work...
-
- const string propFilename = getProperties().getProperty <string>("filename", "");
- const string propMode = getProperties().getProperty <string>("mode", "644");
-
- const size_t maxLineLength =
- std::min(getProperties().getProperty <size_t>("maxlinelength", 46), static_cast <size_t>(46));
-
- size_t total = 0;
- size_t inTotal = 0;
-
- // Output the prelude text ("begin [mode] [filename]")
- out << "begin";
-
- if (!propFilename.empty())
- {
- out << " " << propMode << " " << propFilename;
- total += 2 + propMode.length() + propFilename.length();
- }
-
- out << "\r\n";
- total += 7;
-
- // Process the data
- byte_t inBuffer[64];
- byte_t outBuffer[64];
-
- if (progress)
- progress->start(0);
-
- while (!in.eof())
- {
- // Process up to 45 characters per line
- std::fill(inBuffer, inBuffer + sizeof(inBuffer), 0);
-
- const size_t inLength = in.read(inBuffer, maxLineLength - 1);
-
- outBuffer[0] = UUENCODE(static_cast <unsigned int>(inLength)); // Line length
-
- size_t j = 1;
-
- for (size_t i = 0 ; i < inLength ; i += 3, j += 4)
- {
- const byte_t c1 = inBuffer[i];
- const byte_t c2 = inBuffer[i + 1];
- const byte_t c3 = inBuffer[i + 2];
-
- outBuffer[j] = UUENCODE(c1 >> 2);
- outBuffer[j + 1] = UUENCODE(((c1 << 4) & 060) | ((c2 >> 4) & 017));
- outBuffer[j + 2] = UUENCODE(((c2 << 2) & 074) | ((c3 >> 6) & 03));
- outBuffer[j + 3] = UUENCODE(c3 & 077);
- }
-
- outBuffer[j] = '\r';
- outBuffer[j + 1] = '\n';
-
- out.write(outBuffer, j + 2);
-
- total += j + 2;
- inTotal += inLength;
-
- if (progress)
- progress->progress(inTotal, inTotal);
- }
-
- out << "end\r\n";
- total += 5;
-
- if (progress)
- progress->stop(inTotal);
-
- return (total);
-}
-
-
-size_t uuEncoder::decode(utility::inputStream& in,
- utility::outputStream& out, utility::progressListener* progress)
-{
- in.reset(); // may not work...
-
- // Process the data
- byte_t inBuffer[64];
- byte_t outBuffer[64];
-
- size_t total = 0;
- size_t inTotal = 0;
-
- bool stop = false;
-
- std::fill(inBuffer, inBuffer + sizeof(inBuffer), 0);
-
- if (progress)
- progress->start(0);
-
- while (!stop && !in.eof())
- {
- // Get the line length
- byte_t lengthChar;
-
- if (in.read(&lengthChar, 1) == 0)
- break;
-
- const size_t outLength = UUDECODE(lengthChar);
- const size_t inLength = std::min((outLength * 4) / 3, static_cast <size_t>(64));
- size_t inPos = 0;
-
- switch (lengthChar)
- {
- case ' ':
- case '\t':
- case '\r':
- case '\n':
- {
- // Ignore
- continue;
- }
- case 'b':
- {
- // Read 5 characters more to check for begin ("begin ...\r\n" or "begin ...\n")
- inPos = in.read(inBuffer, 5);
-
- if (inPos == 5 &&
- inBuffer[0] == 'e' &&
- inBuffer[1] == 'g' &&
- inBuffer[2] == 'i' &&
- inBuffer[3] == 'n' &&
- parserHelpers::isSpace(inBuffer[4]))
- {
- inTotal += 5;
-
- byte_t c = 0;
-
- size_t count = 0;
- byte_t buffer[512];
-
- while (count < sizeof(buffer) - 1 && in.read(&c, 1) == 1)
- {
- if (c == '\n')
- break;
-
- buffer[count++] = c;
- }
-
- inTotal += count;
-
- if (c != '\n')
- {
- // OOPS! Weird line. Don't try to decode more...
-
- if (progress)
- progress->stop(inTotal);
-
- return (total);
- }
-
- // Parse filename and mode
- if (count > 0)
- {
- buffer[count] = '\0';
-
- byte_t* p = buffer;
-
- while (*p && parserHelpers::isSpace(*p)) ++p;
-
- byte_t* modeStart = buffer;
-
- while (*p && !parserHelpers::isSpace(*p)) ++p;
-
- getResults()["mode"] = string(modeStart, p);
-
- while (*p && parserHelpers::isSpace(*p)) ++p;
-
- byte_t* filenameStart = buffer;
-
- while (*p && !(*p == '\r' || *p == '\n')) ++p;
-
- getResults()["filename"] = string(filenameStart, p);
- }
- // No filename or mode specified
- else
- {
- getResults()["filename"] = "untitled";
- getResults()["mode"] = 644;
- }
-
- continue;
- }
-
- break;
- }
- case 'e':
- {
- // Read 3 characters more to check for end ("end\r\n" or "end\n")
- inPos = in.read(inBuffer, 3);
-
- if (inPos == 3 &&
- inBuffer[0] == 'n' &&
- inBuffer[1] == 'd' &&
- (inBuffer[2] == '\r' || inBuffer[2] == '\n'))
- {
- stop = true;
- inTotal += 3;
- continue;
- }
-
- break;
- }
-
- }
-
- // Read encoded data
- if (in.read(inBuffer + inPos, inLength - inPos) != inLength - inPos)
- {
- // Premature end of data
- break;
- }
-
- inTotal += (inLength - inPos);
-
- // Decode data
- for (size_t i = 0, j = 0 ; i < inLength ; i += 4, j += 3)
- {
- const byte_t c1 = inBuffer[i];
- const byte_t c2 = inBuffer[i + 1];
- const byte_t c3 = inBuffer[i + 2];
- const byte_t c4 = inBuffer[i + 3];
-
- const size_t n = std::min(inLength - i, static_cast <size_t>(3));
-
- switch (n)
- {
- default:
- case 3: outBuffer[j + 2] = static_cast <byte_t>(UUDECODE(c3) << 6 | UUDECODE(c4));
- case 2: outBuffer[j + 1] = static_cast <byte_t>(UUDECODE(c2) << 4 | UUDECODE(c3) >> 2);
- case 1: outBuffer[j] = static_cast <byte_t>(UUDECODE(c1) << 2 | UUDECODE(c2) >> 4);
- case 0: break;
- }
-
- total += n;
- }
-
- out.write(outBuffer, outLength);
-
- std::fill(inBuffer, inBuffer + sizeof(inBuffer), 0);
-
- if (progress)
- progress->progress(inTotal, inTotal);
- }
-
- if (progress)
- progress->stop(inTotal);
-
- return (total);
-}
-
-
-size_t uuEncoder::getEncodedSize(const size_t n) const
-{
- // 3 bytes of input provide 4 bytes of output.
- // Count CRLF (2 bytes) for each line of 45 characters.
- // Also reserve some space for header and footer.
- return 200 + n * 3 + (n / 45) * 2;
-}
-
-
-size_t uuEncoder::getDecodedSize(const size_t n) const
-{
- // 4 bytes of input provide 3 bytes of output
- return (n * 3) / 4;
-}
-
-
-} // encoder
-} // utility
-} // vmime