Code:
#include "dea.h"
void xor(string &text, string hKey)
{
if(text.size() == hKey.size())
{
for(int i=0; i<text.size(); i++)
{
text.at(i) ^= hKey.at(i);
}
}
}
void appendString(string &text)
{
int size = text.size();
size = size % 16;
for(int i = (16-size); i > 0; i--)
{
text.push_back('x');
}
}
void divyBlocks(string ptext, string &block, int &rem)
{
int size = (ptext.size() / 16);
int mult = size-rem;
int start = (mult * 16);
block.clear();
if(rem > 0)
{
for(int i=0; i<16; i++)
{
block.push_back(ptext.at(start + i));
}
rem--;
}
}
void divideText(string block, string &first, string &second, string &third, string &fourth)
{
first.clear();
second.clear();
third.clear();
fourth.clear();
for(int i=0; i<4; i++)
{
first.push_back(block.at(i));
}
for(int i=4; i<8; i++)
{
second.push_back(block.at(i));
}
for(int i=8; i<12; i++)
{
third.push_back(block.at(i));
}
for(int i=12; i<16; i++)
{
fourth.push_back(block.at(i));
}
}
void ePermutation(string &block)
{
char temp;
char temp2;
for(int i=0; i<3; i++)
{
//shift everything one to the left
temp = block.at(0);
for(int j=3; j>=0; j--)
{
temp2 = block.at(j);
block.at(j) = temp;
temp = temp2;
}
}
}
void dPermutation(string &block)
{
char temp;
char temp2;
for(int i=0; i<3; i++)
{
temp = block.at(3);
for(int j=0; j<4; j++)
{
temp2 = block.at(j);
block.at(j) = temp;
temp = temp2;
}
}
}
void divideKey(string key, string &left, string &right)
{
left.clear();
right.clear();
for(int i=0; i<4; i++)
{
left.push_back(key.at(i));
}
for(int i=4; i<8; i++)
{
right.push_back(key.at(i));
}
}
void encrypt(string &block, string key)
{
string first, second, third, fourth;
divideText(block, first, second, third, fourth);
string kLeft, kRight;
divideKey(key, kLeft, kRight);
//Run the encryption
//ROUND 1
// xor left key and first block
xor(first, kLeft);
// substitute
eSubstitution(second);
// xor right key and 3rd block
xor(third, kRight);
// permutate
ePermutation(fourth);
//ROUND 2
xor(fourth, kLeft);
eSubstitution(first);
xor(second, kRight);
ePermutation(third);
//ROUND 3
xor(third, kLeft);
eSubstitution(fourth);
xor(first, kRight);
ePermutation(second);
//ROUND 4
xor(second, kLeft);
eSubstitution(third);
xor(fourth, kRight);
ePermutation(first);
//FINISHED ONE BLOCK
block.clear();
//reset the block
block = (first + second + third + fourth);
//DONE
}
void decrypt(string &block, string key)
{
string first, second, third, fourth;
divideText(block, first, second, third, fourth);
string kLeft, kRight;
divideKey(key, kLeft, kRight);
//Run the decryption
//ROUND 1
dPermutation(first);
xor(second, kLeft);
dSubstitution(third);
xor(fourth, kRight);
//ROUND 2
xor(first, kRight);
dPermutation(second);
xor(third, kLeft);
dSubstitution(fourth);
//ROUND 3
dSubstitution(first);
xor(second, kRight);
dPermutation(third);
xor(fourth, kLeft);
//ROUND 4
xor(first, kLeft);
dSubstitution(second);
xor(third, kRight);
dPermutation(fourth);
//FINISHED ONE BLOCK
block.clear();
//reset the block
block = (first + second + third + fourth);
//DONE
}
void eSubstitution(string &text)
{
int subTable[256] = {27, 144, 241, 223, 244, 24, 1, 60, 149, 154, 50, 174, 70, 132, 167, 86, 38, 188, 3, 233, 128, 130, 39, 118, 175, 22, 46, 84, 191, 42, 19, 113, 153, 225, 227, 110, 114, 254, 25, 230, 181, 185, 207, 2, 226, 243, 150, 236, 187, 14, 77, 116, 249, 137, 182, 133, 125, 17, 152, 197, 143, 105, 208, 57, 168, 119, 36, 224, 120, 189, 146, 90, 166, 101, 210, 201, 11, 82, 196, 23, 56, 43, 44, 159, 12, 157, 123, 5, 156, 96, 97, 160, 242, 9, 171, 121, 220, 95, 85, 41, 212, 237, 69, 139, 20, 228, 194, 59, 253, 195, 203, 161, 7, 200, 192, 169, 115, 21, 204, 91, 30, 75, 164, 252, 172, 117, 88, 13, 89, 247, 32, 108, 206, 178, 65, 81, 198, 145, 147, 170, 190, 209, 54, 67, 0, 179, 79, 6, 26, 4, 64, 124, 98, 62, 29, 193, 127, 104, 45, 140, 74, 218, 93, 134, 176, 232, 28, 202, 221, 234, 49, 35, 235, 155, 68, 217, 102, 33, 142, 251, 58, 231, 131, 135, 63, 163, 205, 87, 112, 165, 222, 245, 40, 72, 141, 246, 186, 92, 238, 255, 173, 37, 111, 240, 15, 76, 126, 248, 199, 122, 148, 213, 16, 48, 34, 78, 103, 47, 158, 219, 52, 73, 18, 106, 94, 183, 99, 53, 214, 83, 177, 107, 100, 211, 61, 66, 51, 138, 239, 31, 80, 8, 250, 71, 55, 109, 184, 229, 215, 10, 162, 151, 216, 180, 129, 136};
//substitute
for(int i=0; i<4; i++)
{
text.at(i) = ((char)subTable[((int)((unsigned char)text.at(i)))]);
}
}
void dSubstitution(string &text)
{
int subTable[256] = {144, 6, 43, 18, 149, 87, 147, 112, 241, 93, 249, 76, 84, 127, 49, 204, 212, 57, 222, 30, 104, 117, 25, 79, 5, 38, 148, 0, 166, 154, 120, 239, 130, 177, 214, 171, 66, 201, 16, 22, 192, 99, 29, 81, 82, 158, 26, 217, 213, 170, 10, 236, 220, 227, 142, 244, 80, 63, 180, 107, 7, 234, 153, 184, 150, 134, 235, 143, 174, 102, 12, 243, 193, 221, 160, 121, 205, 50, 215, 146, 240, 135, 77, 229, 27, 98, 15, 187, 126, 128, 71, 119, 197, 162, 224, 97, 89, 90, 152, 226, 232, 73, 176, 216, 157, 61, 223, 231, 131, 245, 35, 202, 188, 31, 36, 116, 51, 125, 23, 65, 68, 95, 209, 86, 151, 56, 206, 156, 20, 254, 21, 182, 13, 55, 163, 183, 255, 53, 237, 103, 159, 194, 178, 60, 1, 137, 70, 138, 210, 8, 46, 251, 58, 32, 9, 173, 88, 85, 218, 83, 91, 111, 250, 185, 122, 189, 72, 14, 64, 115, 139, 94, 124, 200, 11, 24, 164, 230, 133, 145, 253, 40, 54, 225, 246, 41, 196, 48, 17, 69, 140, 28, 114, 155, 106, 109, 78, 59, 136, 208, 113, 75, 167, 110, 118, 186, 132, 42, 62, 141, 74, 233, 100, 211, 228, 248, 252, 175, 161, 219, 96, 168, 190, 3, 67, 33, 44, 34, 105, 247, 39, 181, 165, 19, 169, 172, 47, 101, 198, 238, 203, 2, 92, 45, 4, 191, 195, 129, 207, 52, 242, 179, 123, 108, 37, 199};
//substitute
for(int i=0; i<4; i++)
{
text.at(i) = ((char)subTable[((int)((unsigned char)text.at(i)))]);
}
}
void encryptDEA(string &ptext, string key, string &ctext)
{
//CBC Mode
string prevBlock = "";
appendString(ptext);
string block;
int r = ptext.size()/16;
//ENCRYPTION
for(int i=r; i>0; i--)
{
divyBlocks(ptext, block, r);
xor(block, prevBlock);
encrypt(block, key);
prevBlock = block;
ctext += block;
}
}
void decryptDEA(string ctext, string key, string &ptext)
{
//CBC Mode
string block;
int j;
string prevBlock = "";
string xblock = "";
int r = ctext.size()/16;
//DECRYPTION
j = r;
for(int i=0; i<j; i++)
{
divyBlocks(ctext, block, r);
prevBlock = block;
decrypt(block, key);
xor(block, xblock);
xblock = prevBlock;
ptext += block;
}
clearAppend(ptext);
}
void writeFile(string file, string text)
{
file += EXTENSION;
ofstream fout(file.c_str());
for(int i=0; i<text.size(); i++)
{
fout<<((int)text.at(i))<<" ";
}
fout.close();
}
void readFile(string file, string &text)
{
file += EXTENSION;
ifstream fin(file.c_str());
text.clear();
int temp;
vector<int> v;
while(fin>>temp)
{
v.push_back(temp);
}
fin.close();
for(int i=0; i<v.size(); i++)
{
text.push_back((char)v.at(i));
}
}
void convertFile(string file, string ext)
{
if(ext == "dea" || ext == "DEA" || ext == "Dea")
{
//file already converted
}else{
string filename = file + "." + ext;
ifstream fin(filename.c_str());
char ch;
string contents;
while(fin.get(ch))
{
contents+=ch;
}
fin.close();
writeFile(file, contents);
remove(filename.c_str());
}
}
void clearAppend(string &text)
{
int i = text.size();
i--;
while(text.at(i) == 'x')
{
text.erase(text.begin()+i);
i--;
}
}
void deleteFile(string file)
{
//First wipe it
file += EXTENSION;
ofstream fout(file.c_str());
fout.close();
//Then delete the actual file
remove(file.c_str());
}