Main Page | Namespace List | Class Hierarchy | Alphabetical List | Class List | File List | Namespace Members | Class Members | File Members

# basecode.cpp

    00001 // basecode.cpp - written and placed in the public domain by Wei Dai
    00002
    00003 #include "pch.h"
    00004
    00005 #ifndef CRYPTOPP_IMPORTS
    00006
    00007 #include "basecode.h"
    00008 #include "fltrimpl.h"
    00009 #include <ctype.h>
    00010
    00011 NAMESPACE_BEGIN(CryptoPP)
    00012
    00013 void BaseN_Encoder::IsolatedInitialize(const NameValuePairs &parameters)
    00014 {
    00015         parameters.GetRequiredParameter("BaseN_Encoder", Name::EncodingLookupArray(), m_alphabet);
    00016
    00017         parameters.GetRequiredIntParameter("BaseN_Encoder", Name::Log2Base(), m_bitsPerChar);
    00018         if (m_bitsPerChar <= 0 || m_bitsPerChar >= 8)
    00019                 throw InvalidArgument("BaseN_Encoder: Log2Base must be between 1 and 7 inclusive");
    00020
    00021         byte padding;
    00022         bool pad;
    00023         if (parameters.GetValue(Name::PaddingByte(), padding))
    00024                 pad = parameters.GetValueWithDefault(Name::Pad(), true);
    00025         else
    00026                 pad = false;
    00027         m_padding = pad ? padding : -1;
    00028
    00029         m_bytePos = m_bitPos = 0;
    00030
    00031         int i = 8;
    00032         while (i%m_bitsPerChar != 0)
    00033                 i += 8;
    00034         m_outputBlockSize = i/m_bitsPerChar;
    00035
    00036         m_outBuf.New(m_outputBlockSize);
    00037 }
    00038
    00039 unsigned int BaseN_Encoder::Put2(const byte *begin, unsigned int length, int messageEnd, bool blocking)
    00040 {
    00041         FILTER_BEGIN;
    00042         while (m_inputPosition < length)
    00043         {
    00044                 if (m_bytePos == 0)
    00045                         memset(m_outBuf, 0, m_outputBlockSize);
    00046
    00047                 {
    00048                 unsigned int b = begin[m_inputPosition++], bitsLeftInSource = 8;
    00049                 while (true)
    00050                 {
    00051                         assert(m_bitPos < m_bitsPerChar);
    00052                         unsigned int bitsLeftInTarget = m_bitsPerChar-m_bitPos;
    00053                         m_outBuf[m_bytePos] |= b >> (8-bitsLeftInTarget);
    00054                         if (bitsLeftInSource >= bitsLeftInTarget)
    00055                         {
    00056                                 m_bitPos = 0;
    00057                                 ++m_bytePos;
    00058                                 bitsLeftInSource -= bitsLeftInTarget;
    00059                                 if (bitsLeftInSource == 0)
    00060                                         break;
    00061                                 b <<= bitsLeftInTarget;
    00062                                 b &= 0xff;
    00063                         }
    00064                         else
    00065                         {
    00066                                 m_bitPos += bitsLeftInSource;
    00067                                 break;
    00068                         }
    00069                 }
    00070                 }
    00071
    00072                 assert(m_bytePos <= m_outputBlockSize);
    00073                 if (m_bytePos == m_outputBlockSize)
    00074                 {
    00075                         int i;
    00076                         for (i=0; i<m_bytePos; i++)
    00077                         {
    00078                                 assert(m_outBuf[i] < (1 << m_bitsPerChar));
    00079                                 m_outBuf[i] = m_alphabet[m_outBuf[i]];
    00080                         }
    00081                         FILTER_OUTPUT(1, m_outBuf, m_outputBlockSize, 0);
    00082
    00083                         m_bytePos = m_bitPos = 0;
    00084                 }
    00085         }
    00086         if (messageEnd)
    00087         {
    00088                 if (m_bitPos > 0)
    00089                         ++m_bytePos;
    00090
    00091                 int i;
    00092                 for (i=0; i<m_bytePos; i++)
    00093                         m_outBuf[i] = m_alphabet[m_outBuf[i]];
    00094
    00095                 if (m_padding != -1 && m_bytePos > 0)
    00096                 {
    00097                         memset(m_outBuf+m_bytePos, m_padding, m_outputBlockSize-m_bytePos);
    00098                         m_bytePos = m_outputBlockSize;
    00099                 }
    00100                 FILTER_OUTPUT(2, m_outBuf, m_bytePos, messageEnd);
    00101                 m_bytePos = m_bitPos = 0;
    00102         }
    00103         FILTER_END_NO_MESSAGE_END;
    00104 }
    00105
    00106 void BaseN_Decoder::IsolatedInitialize(const NameValuePairs &parameters)
    00107 {
    00108         parameters.GetRequiredParameter("BaseN_Decoder", Name::DecodingLookupArray(), m_lookup);
    00109
    00110         parameters.GetRequiredIntParameter("BaseN_Decoder", Name::Log2Base(), m_bitsPerChar);
    00111         if (m_bitsPerChar <= 0 || m_bitsPerChar >= 8)
    00112                 throw InvalidArgument("BaseN_Decoder: Log2Base must be between 1 and 7 inclusive");
    00113
    00114         m_bytePos = m_bitPos = 0;
    00115
    00116         int i = m_bitsPerChar;
    00117         while (i%8 != 0)
    00118                 i += m_bitsPerChar;
    00119         m_outputBlockSize = i/8;
    00120
    00121         m_outBuf.New(m_outputBlockSize);
    00122 }
    00123
    00124 unsigned int BaseN_Decoder::Put2(const byte *begin, unsigned int length, int messageEnd, bool blocking)
    00125 {
    00126         FILTER_BEGIN;
    00127         while (m_inputPosition < length)
    00128         {
    00129                 unsigned int value;
    00130                 value = m_lookup[begin[m_inputPosition++]];
    00131                 if (value >= 256)
    00132                         continue;
    00133
    00134                 if (m_bytePos == 0 && m_bitPos == 0)
    00135                         memset(m_outBuf, 0, m_outputBlockSize);
    00136
    00137                 {
    00138                         int newBitPos = m_bitPos + m_bitsPerChar;
    00139                         if (newBitPos <= 8)
    00140                                 m_outBuf[m_bytePos] |= value << (8-newBitPos);
    00141                         else
    00142                         {
    00143                                 m_outBuf[m_bytePos] |= value >> (newBitPos-8);
    00144                                 m_outBuf[m_bytePos+1] |= value << (16-newBitPos);
    00145                         }
    00146
    00147                         m_bitPos = newBitPos;
    00148                         while (m_bitPos >= 8)
    00149                         {
    00150                                 m_bitPos -= 8;
    00151                                 ++m_bytePos;
    00152                         }
    00153                 }
    00154
    00155                 if (m_bytePos == m_outputBlockSize)
    00156                 {
    00157                         FILTER_OUTPUT(1, m_outBuf, m_outputBlockSize, 0);
    00158                         m_bytePos = m_bitPos = 0;
    00159                 }
    00160         }
    00161         if (messageEnd)
    00162         {
    00163                 FILTER_OUTPUT(2, m_outBuf, m_bytePos, messageEnd);
    00164                 m_bytePos = m_bitPos = 0;
    00165         }
    00166         FILTER_END_NO_MESSAGE_END;
    00167 }
    00168
    00169 void BaseN_Decoder::InitializeDecodingLookupArray(int *lookup, const byte *alphabet, unsigned int base, bool caseInsensitive)
    00170 {
    00171         std::fill(lookup, lookup+256, -1);
    00172
    00173         for (unsigned int i=0; i<base; i++)
    00174         {
    00175                 if (caseInsensitive && isalpha(alphabet[i]))
    00176                 {
    00177                         assert(lookup[toupper(alphabet[i])] == -1);
    00178                         lookup[toupper(alphabet[i])] = i;
    00179                         assert(lookup[tolower(alphabet[i])] == -1);
    00180                         lookup[tolower(alphabet[i])] = i;
    00181                 }
    00182                 else
    00183                 {
    00184                         assert(lookup[alphabet[i]] == -1);
    00185                         lookup[alphabet[i]] = i;
    00186                 }
    00187         }
    00188 }
    00189
    00190 void Grouper::IsolatedInitialize(const NameValuePairs &parameters)
    00191 {
    00192         m_groupSize = parameters.GetIntValueWithDefault(Name::GroupSize(), 0);
    00193         ConstByteArrayParameter separator, terminator;
    00194         if (m_groupSize)
    00195                 parameters.GetRequiredParameter("Grouper", Name::Separator(), separator);
    00196         else
    00197                 parameters.GetValue(Name::Separator(), separator);
    00198         parameters.GetValue(Name::Terminator(), terminator);
    00199
    00200         m_separator.Assign(separator.begin(), separator.size());
    00201         m_terminator.Assign(terminator.begin(), terminator.size());
    00202         m_counter = 0;
    00203 }
    00204
    00205 unsigned int Grouper::Put2(const byte *begin, unsigned int length, int messageEnd, bool blocking)
    00206 {
    00207         FILTER_BEGIN;
    00208         if (m_groupSize)
    00209         {
    00210                 while (m_inputPosition < length)
    00211                 {
    00212                         if (m_counter == m_groupSize)
    00213                         {
    00214                                 FILTER_OUTPUT(1, m_separator, m_separator.size(), 0);
    00215                                 m_counter = 0;
    00216                         }
    00217
    00218                         unsigned int len;
    00219                         FILTER_OUTPUT2(2, len = STDMIN(length-m_inputPosition, m_groupSize-m_counter),
    00220                                 begin+m_inputPosition, len, 0);
    00221                         m_inputPosition += len;
    00222                         m_counter += len;
    00223                 }
    00224         }
    00225         else
    00226                 FILTER_OUTPUT(3, begin, length, 0);
    00227
    00228         if (messageEnd)
    00229         {
    00230                 FILTER_OUTPUT(4, m_terminator, m_terminator.size(), messageEnd);
    00231                 m_counter = 0;
    00232         }
    00233         FILTER_END_NO_MESSAGE_END
    00234 }
    00235
    00236 NAMESPACE_END
    00237
    00238 #endif