00001
00002
00003 #include "pch.h"
00004 #include "tea.h"
00005 #include "misc.h"
00006
00007 NAMESPACE_BEGIN(CryptoPP)
00008
00009 static const word32 DELTA = 0x9e3779b9;
00010 typedef BlockGetAndPut<word32, BigEndian> Block;
00011
00012 void TEA::Base::UncheckedSetKey(const byte *userKey, unsigned int length, const NameValuePairs ¶ms)
00013 {
00014 AssertValidKeyLength(length);
00015
00016 GetUserKey(BIG_ENDIAN_ORDER, m_k.begin(), 4, userKey, KEYLENGTH);
00017 m_limit = GetRoundsAndThrowIfInvalid(params, this) * DELTA;
00018 }
00019
00020 void TEA::Enc::ProcessAndXorBlock(const byte *inBlock, const byte *xorBlock, byte *outBlock) const
00021 {
00022 word32 y, z;
00023 Block::Get(inBlock)(y)(z);
00024
00025 word32 sum = 0;
00026 while (sum != m_limit)
00027 {
00028 sum += DELTA;
00029 y += (z << 4) + m_k[0] ^ z + sum ^ (z >> 5) + m_k[1];
00030 z += (y << 4) + m_k[2] ^ y + sum ^ (y >> 5) + m_k[3];
00031 }
00032
00033 Block::Put(xorBlock, outBlock)(y)(z);
00034 }
00035
00036 void TEA::Dec::ProcessAndXorBlock(const byte *inBlock, const byte *xorBlock, byte *outBlock) const
00037 {
00038 word32 y, z;
00039 Block::Get(inBlock)(y)(z);
00040
00041 word32 sum = m_limit;
00042 while (sum != 0)
00043 {
00044 z -= (y << 4) + m_k[2] ^ y + sum ^ (y >> 5) + m_k[3];
00045 y -= (z << 4) + m_k[0] ^ z + sum ^ (z >> 5) + m_k[1];
00046 sum -= DELTA;
00047 }
00048
00049 Block::Put(xorBlock, outBlock)(y)(z);
00050 }
00051
00052 void XTEA::Base::UncheckedSetKey(const byte *userKey, unsigned int length, const NameValuePairs ¶ms)
00053 {
00054 AssertValidKeyLength(length);
00055
00056 GetUserKey(BIG_ENDIAN_ORDER, m_k.begin(), 4, userKey, KEYLENGTH);
00057 m_limit = GetRoundsAndThrowIfInvalid(params, this) * DELTA;
00058 }
00059
00060 void XTEA::Enc::ProcessAndXorBlock(const byte *inBlock, const byte *xorBlock, byte *outBlock) const
00061 {
00062 word32 y, z;
00063 Block::Get(inBlock)(y)(z);
00064
00065 #ifdef __SUNPRO_CC
00066
00067 size_t sum = 0;
00068 while ((sum&0xffffffff) != m_limit)
00069 #else
00070 word32 sum = 0;
00071 while (sum != m_limit)
00072 #endif
00073 {
00074 y += (z<<4 ^ z>>5) + z ^ sum + m_k[sum&3];
00075 sum += DELTA;
00076 z += (y<<4 ^ y>>5) + y ^ sum + m_k[sum>>11 & 3];
00077 }
00078
00079 Block::Put(xorBlock, outBlock)(y)(z);
00080 }
00081
00082 void XTEA::Dec::ProcessAndXorBlock(const byte *inBlock, const byte *xorBlock, byte *outBlock) const
00083 {
00084 word32 y, z;
00085 Block::Get(inBlock)(y)(z);
00086
00087 #ifdef __SUNPRO_CC
00088
00089 size_t sum = m_limit;
00090 while ((sum&0xffffffff) != 0)
00091 #else
00092 word32 sum = m_limit;
00093 while (sum != 0)
00094 #endif
00095 {
00096 z -= (y<<4 ^ y>>5) + y ^ sum + m_k[sum>>11 & 3];
00097 sum -= DELTA;
00098 y -= (z<<4 ^ z>>5) + z ^ sum + m_k[sum&3];
00099 }
00100
00101 Block::Put(xorBlock, outBlock)(y)(z);
00102 }
00103
00104 #define MX (z>>5^y<<2)+(y>>3^z<<4)^(sum^y)+(m_k[p&3^e]^z)
00105
00106 void BTEA::Enc::ProcessAndXorBlock(const byte *inBlock, const byte *xorBlock, byte *outBlock) const
00107 {
00108 unsigned int n = m_blockSize / 4;
00109 word32 *v = (word32*)outBlock;
00110 ConditionalByteReverse(BIG_ENDIAN_ORDER, v, (const word32*)inBlock, m_blockSize);
00111
00112 word32 y = v[0], z = v[n-1], e;
00113 word32 p, q = 6+52/n;
00114 word32 sum = 0;
00115
00116 while (q-- > 0)
00117 {
00118 sum += DELTA;
00119 e = sum>>2 & 3;
00120 for (p = 0; p < n-1; p++)
00121 {
00122 y = v[p+1];
00123 z = v[p] += MX;
00124 }
00125 y = v[0];
00126 z = v[n-1] += MX;
00127 }
00128
00129 ConditionalByteReverse(BIG_ENDIAN_ORDER, v, v, m_blockSize);
00130 }
00131
00132 void BTEA::Dec::ProcessAndXorBlock(const byte *inBlock, const byte *xorBlock, byte *outBlock) const
00133 {
00134 unsigned int n = m_blockSize / 4;
00135 word32 *v = (word32*)outBlock;
00136 ConditionalByteReverse(BIG_ENDIAN_ORDER, v, (const word32*)inBlock, m_blockSize);
00137
00138 word32 y = v[0], z = v[n-1], e;
00139 word32 p, q = 6+52/n;
00140 word32 sum = q * DELTA;
00141
00142 while (sum != 0)
00143 {
00144 e = sum>>2 & 3;
00145 for (p = n-1; p > 0; p--)
00146 {
00147 z = v[p-1];
00148 y = v[p] -= MX;
00149 }
00150
00151 z = v[n-1];
00152 y = v[0] -= MX;
00153 sum -= DELTA;
00154 }
00155
00156 ConditionalByteReverse(BIG_ENDIAN_ORDER, v, v, m_blockSize);
00157 }
00158
00159 NAMESPACE_END