I want to claculate the MAC(Message Authentication Code) CBC chiper(Ansi x9.9), i found a sample which calculates the MAC based on a cycle, in each round the encrypted reuslt must be XOR with next round plain Text block and the result should be encrepted to being used to next step and this cycle repeats for 4 times till the last encrypted value must be return as MAC.
Cryptographic Key = 0123456789abcdef
The text is the ASCII code for "7654321 Now is the time for ".
Text = 37363534333231204e6f77206873207468652074696d6520666f7220
TIME --- PLAIN TEXT---------------DES INPUT BLOCK -------- DES OUTPUT BLOCK
1 ---- 3736353433323120 -------- 3736353433323120 -------- 21fb193693a16c28
2 ---- 4e6f772068732074 -------- 6f946e16fad24c5c -------- 6c463f0cb7167a6f
3 ---- 68652074696d6520 -------- 04231f78de7b1f4f -------- 956ee891e889d91e
4 ---- 666f722000000000 -------- f3019ab1e889d91e -------- f1d30f6849312ca4
I tried to implement this sample. at the first step i got the same result as the sample but for the next step my Des encryption function returns the different resutl as the sample's 2th step. i used a hardware device to encrypt each Des input block, it returns the same DES output block as the sample return. either i found another DES implementation sample here it reutrns the correct encrption too. but my app which uses microsft example on msdn returns the incorrect result for steps 2,3 and 4 except step 1. here is my code:
public byte[] EncryptPart(byte[] toEncrypt, byte[] Key, byte[] IV)
{
try
{
MemoryStream mStream = new MemoryStream();
DES DESalg = DES.Create();
DESalg.Mode = CipherMode.CBC;
DESalg.Padding = PaddingMode.None;
CryptoStream cStream = new CryptoStream(mStream,
DESalg.CreateEncryptor(Key, IV),
CryptoStreamMode.Write);
cStream.Write(toEncrypt, 0, toEncrypt.Length);
cStream.FlushFinalBlock();
byte[] ret = mStream.ToArray();
cStream.Close();
mStream.Close();
return ret;
}
catch (CryptographicException e)
{
Console.WriteLine("A Cryptographic error occurred: {0}", e.Message);
return null;
}
}
and here where i have used that function
var IV = new byte[8];//empty byte array
var key = new byte[] { 0x01, 0x23, 0x45, 0x67, 0x89, 0xab, 0xcd, 0xef };
var result = new byte[8];
int LoopCount = data.Length / 8;
for (int i = 0; i < LoopCount; i++)
{
byte[] Part= new byte[8];
Array.Copy(data, i * 8, Part, 0, 8);
Part = XorArray(Part, result);
result = EncryptPart(Part, key, IV);
}
int remain=data.Length % 8;
if (remain != 0)
{
byte[] LastPart = new byte[8];//
Array.Copy(data, data.Length - remain, LastPart, 0, remain);
LastPart=XorArray(LastPart, result);
result = EncryptPart(LastPart, key, IV);
}