- Main Page
- Namespaces
- Classes
- Files

- File List
- File Members

# seal.cpp

    00001 // seal.cpp - written and placed in the public domain by Wei Dai
    00002 // updated to SEAL 3.0 by Leonard Janke
    00003
    00004 #include "pch.h"
    00005
    00006 // prevent Sun's CC compiler from including this file automatically
    00007 #if !(defined(__SUNPRO_CC) && defined(CRYPTOPP_ITERHASH_H))
    00008
    00009 #include "seal.h"
    00010 #include "sha.h"
    00011 #include "misc.h"
    00012
    00013 NAMESPACE_BEGIN(CryptoPP)
    00014
    00015 void SEAL_TestInstantiations()
    00016 {
    00017         SEAL<>::Encryption x;
    00018 }
    00019
    00020 struct SEAL_Gamma
    00021 {
    00022         SEAL_Gamma(const byte *key)
    00023                 : H(5), Z(5), D(16), lastIndex(0xffffffff)
    00024         {
    00025                 GetUserKey(BIG_ENDIAN_ORDER, H.begin(), 5, key, 20);
    00026                 memset(D, 0, 64);
    00027         }
    00028
    00029         word32 Apply(word32 i);
    00030
    00031         SecBlock<word32> H, Z, D;
    00032         word32 lastIndex;
    00033 };
    00034
    00035 word32 SEAL_Gamma::Apply(word32 i)
    00036 {
    00037         word32 shaIndex = i/5;
    00038         if (shaIndex != lastIndex)
    00039         {
    00040                 memcpy(Z, H, 20);
    00041                 D[0] = shaIndex;
    00042                 SHA::Transform(Z, D);
    00043                 lastIndex = shaIndex;
    00044         }
    00045         return Z[i%5];
    00046 }
    00047
    00048 template <class B>
    00049 void SEAL_Policy<B>::CipherSetKey(const NameValuePairs &params, const byte *key, size_t length)
    00050 {
    00051         m_insideCounter = m_outsideCounter = m_startCount = 0;
    00052
    00053         unsigned int L = params.GetIntValueWithDefault("NumberOfOutputBitsPerPositionIndex", 32*1024);
    00054         m_iterationsPerCount = L / 8192;
    00055
    00056         SEAL_Gamma gamma(key);
    00057         unsigned int i;
    00058
    00059         for (i=0; i<512; i++)
    00060                 m_T[i] = gamma.Apply(i);
    00061
    00062         for (i=0; i<256; i++)
    00063                 m_S[i] = gamma.Apply(0x1000+i);
    00064
    00065         m_R.New(4*(L/8192));
    00066
    00067         for (i=0; i<m_R.size(); i++)
    00068                 m_R[i] = gamma.Apply(0x2000+i);
    00069 }
    00070
    00071 template <class B>
    00072 void SEAL_Policy<B>::CipherResynchronize(byte *keystreamBuffer, const byte *IV)
    00073 {
    00074         m_outsideCounter = IV ? UnalignedGetWord<word32>(BIG_ENDIAN_ORDER, IV) : 0;
    00075         m_startCount = m_outsideCounter;
    00076         m_insideCounter = 0;
    00077 }
    00078
    00079 template <class B>
    00080 void SEAL_Policy<B>::SeekToIteration(lword iterationCount)
    00081 {
    00082         m_outsideCounter = m_startCount + (unsigned int)(iterationCount / m_iterationsPerCount);
    00083         m_insideCounter = (unsigned int)(iterationCount % m_iterationsPerCount);
    00084 }
    00085
    00086 template <class B>
    00087 void SEAL_Policy<B>::OperateKeystream(KeystreamOperation operation, byte *output, const byte *input, size_t iterationCount)
    00088 {
    00089         KeystreamOutput<B> keystreamOutput(operation, output, input);
    00090         word32 a, b, c, d, n1, n2, n3, n4;
    00091         unsigned int p, q;
    00092
    00093         for (size_t iteration = 0; iteration < iterationCount; ++iteration)
    00094         {
    00095 #define Ttab(x) *(word32 *)((byte *)m_T.begin()+x)
    00096
    00097                 a = m_outsideCounter ^ m_R[4*m_insideCounter];
    00098                 b = rotrFixed(m_outsideCounter, 8U) ^ m_R[4*m_insideCounter+1];
    00099                 c = rotrFixed(m_outsideCounter, 16U) ^ m_R[4*m_insideCounter+2];
    00100                 d = rotrFixed(m_outsideCounter, 24U) ^ m_R[4*m_insideCounter+3];
    00101
    00102                 for (unsigned int j=0; j<2; j++)
    00103                 {
    00104                         p = a & 0x7fc;
    00105                         b += Ttab(p);
    00106                         a = rotrFixed(a, 9U);
    00107
    00108                         p = b & 0x7fc;
    00109                         c += Ttab(p);
    00110                         b = rotrFixed(b, 9U);
    00111
    00112                         p = c & 0x7fc;
    00113                         d += Ttab(p);
    00114                         c = rotrFixed(c, 9U);
    00115
    00116                         p = d & 0x7fc;
    00117                         a += Ttab(p);
    00118                         d = rotrFixed(d, 9U);
    00119                 }
    00120
    00121                 n1 = d, n2 = b, n3 = a, n4 = c;
    00122
    00123                 p = a & 0x7fc;
    00124                 b += Ttab(p);
    00125                 a = rotrFixed(a, 9U);
    00126
    00127                 p = b & 0x7fc;
    00128                 c += Ttab(p);
    00129                 b = rotrFixed(b, 9U);
    00130
    00131                 p = c & 0x7fc;
    00132                 d += Ttab(p);
    00133                 c = rotrFixed(c, 9U);
    00134
    00135                 p = d & 0x7fc;
    00136                 a += Ttab(p);
    00137                 d = rotrFixed(d, 9U);
    00138
    00139                 // generate 8192 bits
    00140                 for (unsigned int i=0; i<64; i++)
    00141                 {
    00142                         p = a & 0x7fc;
    00143                         a = rotrFixed(a, 9U);
    00144                         b += Ttab(p);
    00145                         b ^= a;
    00146
    00147                         q = b & 0x7fc;
    00148                         b = rotrFixed(b, 9U);
    00149                         c ^= Ttab(q);
    00150                         c += b;
    00151
    00152                         p = (p+c) & 0x7fc;
    00153                         c = rotrFixed(c, 9U);
    00154                         d += Ttab(p);
    00155                         d ^= c;
    00156
    00157                         q = (q+d) & 0x7fc;
    00158                         d = rotrFixed(d, 9U);
    00159                         a ^= Ttab(q);
    00160                         a += d;
    00161
    00162                         p = (p+a) & 0x7fc;
    00163                         b ^= Ttab(p);
    00164                         a = rotrFixed(a, 9U);
    00165
    00166                         q = (q+b) & 0x7fc;
    00167                         c += Ttab(q);
    00168                         b = rotrFixed(b, 9U);
    00169
    00170                         p = (p+c) & 0x7fc;
    00171                         d ^= Ttab(p);
    00172                         c = rotrFixed(c, 9U);
    00173
    00174                         q = (q+d) & 0x7fc;
    00175                         d = rotrFixed(d, 9U);
    00176                         a += Ttab(q);
    00177
    00178                         keystreamOutput (b + m_S[4*i+0])
    00179                                                         (c ^ m_S[4*i+1])
    00180                                                         (d + m_S[4*i+2])
    00181                                                         (a ^ m_S[4*i+3]);
    00182
    00183                         if (i & 1)
    00184                         {
    00185                                 a += n3;
    00186                                 b += n4;
    00187                                 c ^= n3;
    00188                                 d ^= n4;
    00189                         }
    00190                         else
    00191                         {
    00192                                 a += n1;
    00193                                 b += n2;
    00194                                 c ^= n1;
    00195                                 d ^= n2;
    00196                         }
    00197                 }
    00198
    00199                 if (++m_insideCounter == m_iterationsPerCount)
    00200                 {
    00201                         ++m_outsideCounter;
    00202                         m_insideCounter = 0;
    00203                 }
    00204         }
    00205
    00206         a = b = c = d = n1 = n2 = n3 = n4 = 0;
    00207         p = q = 0;
    00208 }
    00209
    00210 template class SEAL_Policy<BigEndian>;
    00211 template class SEAL_Policy<LittleEndian>;
    00212
    00213 NAMESPACE_END
    00214
    00215 #endif