Screenshot of the tool, and the test procedures of the tool are as follows:
Encrypt:
Result after encrypting:
Decrypt:
Result after decrypting:
Introduction
This article introduces how to use the Rijndael to encrypt any file, such as *.jpg, *.doc... and decrypt the encrypted file.
Background
I promised my friend to help her to program one encrypt & decrypt tool for the examination,^-^. I searched some articles, but without the implementation of Rijndael, so I decided to do the Rijndael with the help of the MSDN.
Using the Code
The whole code is in the attachment. You can download it if you prefer, or use it directly. Files in the attachment are as follows:
Aes.cs is the implementation of the Rijndael, and the main functions are Cipher
and InvCipher
.
public void Cipher(byte[] input, byte[] output)
{
this.State = new byte[4, Nb];
for (int i = 0; i < (4 * Nb); ++i)
{
this.State[i % 4, i / 4] = input[i];
}
AddRoundKey(0);
for (int round = 1; round <= (Nr - 1); ++round)
{
SubBytes();
ShiftRows();
MixColumns();
AddRoundKey(round);
}
SubBytes();
ShiftRows();
AddRoundKey(Nr);
for (int i = 0; i < (4 * Nb); ++i)
{
output[i] = this.State[i % 4, i / 4];
}
}
public void InvCipher(byte[] input, byte[] output)
{
this.State = new byte[4, Nb];
for (int i = 0; i < (4 * Nb); ++i)
{
this.State[i % 4, i / 4] = input[i];
}
AddRoundKey(Nr);
for (int round = Nr - 1; round >= 1; --round)
{
InvShiftRows();
InvSubBytes();
AddRoundKey(round);
InvMixColumns();
}
InvShiftRows();
InvSubBytes();
AddRoundKey(0);
for (int i = 0; i < (4 * Nb); ++i)
{
output[i] = this.State[i % 4, i / 4];
}
}
RijndaelFrm.cs: The window of encryption & decryption by the Rijndael and the two functions(
Encrypt
&
Decrypt
) in
RijndaelFrm.cs called the IF of the class Aes for encryption and decryption. You can get detailed information from the class.
private Boolean Encrypt(string cOpenFile,string cSaveFile,string cPassword)
{
if (("" == cOpenFile) ||
("" == cSaveFile) ||
("" == cPassword))
{
return false;
}
if (false == File.Exists(cOpenFile))
{
return false;
}
while (true == File.Exists(cSaveFile))
{
cSaveFile = Rename(cSaveFile);
}
byte[] plainText = new byte[MAX_BLOCK_LENGTH];
byte[] cipherText = new byte[MAX_BLOCK_LENGTH];
byte[] bzkey = new byte[MAX_KEY_LENGTH];
bzkey = Encoding.Unicode.GetBytes(cPassword);
FileStream fileStream = new FileStream(cOpenFile, FileMode.Open);
fileStream.Seek(0, SeekOrigin.Begin);
FileStream saveStream = new FileStream(cSaveFile, FileMode.Append);
long lFileLength = fileStream.Length;
long lPostion = fileStream.Position;
while (lPostion < lFileLength)
{
Initialize(plainText, MAX_BLOCK_LENGTH);
long lHasRead = fileStream.Read(plainText, 0, MAX_BLOCK_LENGTH);
if (0 >= lHasRead)
{
break;
}
lPostion = fileStream.Position;
Aes aes = new Aes(ekeySize, bzkey, eblockSize);
Initialize(cipherText, MAX_BLOCK_LENGTH);
aes.Cipher(plainText, cipherText);
saveStream.Write(cipherText, 0, MAX_BLOCK_LENGTH);
}
saveStream.Close();
fileStream.Close();
return true;
}
private Boolean Decrypt(string cOpenFile, string cSaveFile, string cPassword)
{
if (("" == cOpenFile) ||
("" == cSaveFile) ||
("" == cPassword))
{
return false;
}
if (0 > cOpenFile.LastIndexOf(".aes"))
{
return false;
}
if (false == File.Exists(cOpenFile))
{
return false;
}
while (true == File.Exists(cSaveFile))
{
cSaveFile = Rename(cSaveFile);
}
byte[] plainText = new byte[MAX_BLOCK_LENGTH];
byte[] cipherText = new byte[MAX_BLOCK_LENGTH];
byte[] bzkey = new byte[MAX_KEY_LENGTH];
bzkey = Encoding.Unicode.GetBytes(cPassword);
FileStream fileStream = new FileStream(cOpenFile, FileMode.Open);
fileStream.Seek(0, SeekOrigin.Begin);
FileStream saveStream = new FileStream(cSaveFile, FileMode.Append);
long lFileLength = fileStream.Length;
long lPostion = fileStream.Position;
while (lPostion < lFileLength)
{
Initialize(plainText, MAX_BLOCK_LENGTH);
long lHasRead = fileStream.Read(plainText, 0, MAX_BLOCK_LENGTH);
if (0 >= lHasRead)
{
break;
}
lPostion = fileStream.Position;
Aes aes = new Aes(ekeySize, bzkey, eblockSize);
Initialize(cipherText, MAX_BLOCK_LENGTH);
aes.InvCipher(plainText, cipherText);
saveStream.Write(cipherText, 0, MAX_BLOCK_LENGTH);
}
saveStream.Close();
fileStream.Close();
return true;
}
Or you can transform the aes.cs to your project, and call the IF as shown above. You can easily encrypt or decrypt any of your files.
Note
The form is only compatible with the password whose max length is 128 bits, but the algorithm of the aes is compatible with the password whose max length can be 128, 192 or 256 bits. The user can complete this, or I could complete it later.
History
- 2009-06-20: First build ver. 1.01