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

Generated on Sat Jan 22 09:44:34 2005 for Crypto++ by  doxygen 1.4.0