Showing posts with label Cryptography. Show all posts
Showing posts with label Cryptography. Show all posts

Tuesday, March 27, 2012

Disk Cipher Algorithms in C

The disk cipher is a combination of the Caesar Cipher and the Simple Substitution Cipher. It resembles  the Simple Substitution Cipher because it uses two predefined alphabets and it resembles the Caesar Cipher because the substitution is done according to a predefined shift.

Learn more about the Caesar Cipher.
Learn more about the Simple Substitution Cipher.

If you want to read more about the history of the disk cipher, you can check out  this article.

In order to implement the algorithm in C, we shall use the following enumeration who shall reflect if an encoding/decoding operation was completed correctly.
typedef enum
{
 OPERATION_SUCCESS = 1U,
 OPERATION_FAILED = 0U,
}OPERATION_STATUS;
1.The Encoding Algorithm

The encoding algorithm is very similar to the one used for the Simple Substitution Cipher, except that the shift will be added to the position (and a modulo operation shall be used in order to avoid overflow).  In order to obtain the position of the encoded symbol, the following formula shall be used:
where:
  • j - the position of the symbol in the cipher text (coded alphabet)
  • Ei - the position of the symbol from the original message in the original alphabet (plain text)
  • s - the shift value
  • O - the original alphabet
OPERATION_STATUS DiskCipher_Encode(char* originalAlphabet,
                                   char* codedAlphabet,
                                   char* originalMessage,
                                   char* encodedMessage,
                                   unsigned short shift)
{
 unsigned short alphabetLength = strlen(originalAlphabet);
 unsigned int messageLength    = strlen(originalMessage);
 unsigned int i = 0U;
 char* pointer = NULL;
 unsigned int position = 0U;
 if( alphabetLength != strlen(codedAlphabet) )
 {
  //The lengths of the alphabets do not match
  return OPERATION_FAILED;
 }
 for(i=0; i<messageLength; i++)
 {
  pointer  = strchr(originalAlphabet, originalMessage[i]);
  if(pointer==NULL)
  {
   //A character in the message was not found in the
   //original alphabet
   return OPERATION_FAILED;
  }
  else
  {
   position = ((pointer - originalAlphabet) + shift)%alphabetLength;
   encodedMessage[i] = codedAlphabet[position];
  }
 }
 encodedMessage[messageLength] = '\0';
 return OPERATION_SUCCESS;
}
The function receives 5 parameters:
  • originalAlphabet - a pointer to a string containing the plain text alphabet (who has all the letters that appear in the originalMessage). All symbols in the originalAlphabet should appear only once.
  • codedAlphabet - a pointer to a string containing the cipher text alphabet (who has the same length as the originalAlphabet string). All symbols in the codedAlphabet should appear only once.
  • originalMessage - a pointer to a string containing the message who will be encoded
  • codedMessage - a pointer to a pre-allocated empty string who will contain the encoded message.
  • shift - what is the offset value used for the substitution
The function returns OPERATIONS_SUCCES if all preconditions have been respected, respectively OPERATON_FAILED if the lengths of the alphabets are different or if the function found a symbol in the original message who has not been defined in the originalAlphabet.

2.The Decoding Algorithm

The decoding algorithm shall do the inverse operation of encoding. Instead of adding the shift, the shift will be subtracted. In order to obtain the position of the decoded symbol, the following formula shall be used:
where:
                                       
  • j - the position of decoded symbol in the plain text (original Alphabet)
  • Ci - the position of the symbol from the encoded message in the cipher text (coded alphabet)
  • s - the shift value
  • O - the length of the original alphabet
OPERATION_STATUS DiskCipher_Decode(char* originalAlphabet,
                                   char* codedAlphabet,
                                   char* encodedMessage,
                                   char* decodedMessage,
                                   unsigned short shift)
{
 unsigned short alphabetLength = strlen(originalAlphabet);
 unsigned int messageLength    = strlen(encodedMessage);
 unsigned int i = 0U;
 char* pointer = NULL;
 unsigned int position = 0U;
 if( alphabetLength != strlen(codedAlphabet) )
 {
  //The lengths of the alphabets do not match
  return OPERATION_FAILED;
 }
 for(i=0; i<messageLength; i++)
 {
  pointer  = strchr(codedAlphabet, encodedMessage[i]);
  if(pointer==NULL)
  {
   //A character in the message was not found in the
   //coded alphabet
   return OPERATION_FAILED;
  }
  else
  {
   position = (abs(alphabetLength + (pointer - codedAlphabet) - shift))
      %alphabetLength;
   decodedMessage[i] = originalAlphabet[position];
  }
 }
 decodedMessage[messageLength] = '\0';
 return OPERATION_SUCCESS;
}
The function receives 5 parameters:
  • originalAlphabet - a pointer to a string containing the plain text alphabet (who has all the letters that appear in the originalMessage). All symbols in the originalAlphabet should appear only once.
  • codedAlphabet - a pointer to a string containing the cipher text alphabet (who has the same length as the originalAlphabet string). All symbols in the codedAlphabet should appear only once.
  • encodedMessage - a pointer to a string containing the message who will be encoded
  • decodedMessage - a pointer to a pre-allocated empty string who will contain the decoded message.
  • shift - what is the offset value used for the substitution
The function returns OPERATIONS_SUCCES if all preconditions have been respected, respectively OPERATON_FAILED if the lengths of the alphabets are different or if the function found a symbol in the encoded message who has not been defined in the coded Alphabet.

3.Example
Here's a short example on how to use the functions described above:
char originalAlphabet[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZ ";
char codedAlphabet[]    = "QWERTYUIOPASDFGHJKLZXCVBNM#";
char originalMessage[]  = "DISK CIPHER";
char encodedMessage[12];
char decodedMessage[12];
unsigned int shift = 15;
DiskCipher_Encode(originalAlphabet, codedAlphabet,
    originalMessage, encodedMessage,shift);
puts(encodedMessage);
DiskCipher_Decode(originalAlphabet, codedAlphabet,
    encodedMessage, decodedMessage,shift);
puts(decodedMessage);

Saturday, March 24, 2012

Simple Substitution Cipher Algorithms in C

A substitution cipher is a method of encryption by which units of the original alphabet (or plain text) are replaced with units of a coded alphabet (or cipher text) according to a regular system. The units may be single letters, two letters or triplets or letters, etc. A simple substitution cipher uses operates with single letter units.

To encrypt a message using a substitution cipher one needs the plain text alphabet (original alphabet) and the cipher text alphabet (the coded alphabet) which shall serve as a private key.
The formula for the substitution is:
  • Ei represents the i-th character from the encoded string
  • Cj represents the j-th character from the cipher text alphabet, where j represents the position of the Ei character in the original alphabet.
In order to implement such algorithm we shall define the following enumeration:
typedef enum
{
 OPERATION_SUCCESS = 1U,
 OPERATION_FAILED  = 0U
}OPERATION_STATUS;
Below you can see the C implementation for the algorithm:
OPERATION_STATUS SimpleSubstitutionCipher_Code(char* originalAlphabet,
                                               char* codedAlphabet,
                                               char* originalMessage,
                                               char* encodedMessage)
{
 unsigned short alphabetLength = strlen(originalAlphabet);
 unsigned int messageLength    = strlen(originalMessage);
 unsigned int i = 0U;
 char* pointer = NULL;
 unsigned int position = 0U;
 if( alphabetLength != strlen(codedAlphabet) )
 {
  //The lengths of the alphabets do not match
  return OPERATION_FAILED;
 }
 for(i=0; i<messageLength; i++)
 {
  pointer  = strchr(originalAlphabet, originalMessage[i]);
  if(pointer==NULL)
  {
   //A character in the message was not found in the
   //original alphabet
   return OPERATION_FAILED;
  }
  else
  {
   position = pointer - originalAlphabet;
   encodedMessage[i] = codedAlphabet[position];
  }
 }
 encodedMessage[messageLength] = '\0';
 return OPERATION_SUCCESS;
}
The function receives 4 parameters:
  • originalAlphabet - a pointer to a string containing the plain text alphabet (who has all the letters that appear in the originalMessage). All symbols in the originalAlphabet should appear only once.
  • codedAlphabet - a pointer to a string containing the cipher text alphabet (who has the same length as the originalAlphabet string). All symbols in the codedAlphabet should appear only once.
  • originalMessage - a pointer to a string containing the message who will be encoded
  • codedMessage - a pointer to a pre-allocated empty string who will contain the encoded message.
The function returns OPERATIONS_SUCCES if all preconditions have been respected, respectively OPERATON_FAILED if the lengths of the alphabets are different or if the function found a symbol in the original message who has not been defined in the originalAlphabet.

A simple encoding/decoding example
 char originalAlphabet[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZ ";
 char codedAlphabet[]    = "QWERTYUIOPASDFGHJKLZXCVBNM#";
 char originalMessage[]  = "SUBSTITUTION CIPHER";
 char encodedMessage[20];
 char decodedMessage[20];
 //Encoding
 SimpleSubstitutionCipher_Code(originalAlphabet,codedAlphabet,
                               originalMessage, encodedMessage);
 puts(encodedMessage);
 //Decoding
 SimpleSubstitutionCipher_Code(codedAlphabet,originalAlphabet,
                               encodedMessage, decodedMessage);
 puts(decodedMessage);
As you probably already observed, the same function is used for both encryption and decryption. This is because the same operations are performed in both cases.

Friday, February 24, 2012

Caesar Cipher Algorithms in C

The Caesar cipher is one of the simplest and most widely known encryption techniques. The method consists in replacing each letter with another letter who is s positions to the right, where s is a number who was fixed before.

If you want to read more about the Caesar cipher (especially the history behind it), you should probably see this.

For the C implementation we shall consider the following macrodefinitions, enumerations and libraries:
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<ctype.h>

#define SHIFT_MAX      26
#define NUMBER_OF_LETTERS    26
#define NUMBER_OF_DIGITS    10
#define CAESAR_CIPHER_SPECIAL_CHARS  " .!?,;:'()[]{}`"

typedef enum
{
 OPERATION_SUCCESS = 1U,
 OPERATION_FAILED  = 0U
}OPERATION_STATUS;
1. The Encryption Algorithm
We shall consider E as the encrypted ASCII string and O as the "original" ASCII string. E is calculated using the formulas displayed below:
Caesar cipher encryption formulas
  • Oi - the element at  the i-th position in the original string.
  • Ei -  the element at  the i-th position in the encrypted string.
  • M - a predefined set of elements who will not be encrypted (this set will be contained in CAESAR_CIPHER_SPECIAL_CHARS).
  • s - how many positions a letter or a digit will be shifted
  • The "magic numbers" 97, 65 and 48 represent the ASCII codes of 'a', 'A' and '0', while 26 and 10 represent the number of letters of the English alphabet respectively the number of digits. 
Example (s=3) :
The original string    : I AM CAESAR
The encrypted string: L DP FDHVDU

The C implementation:
OPERATION_STATUS CaesarCipher_Encrypt(const char* originalMessage,
                                      char* codedMessage,
                                      short shift)
{
 unsigned int size = strlen(originalMessage);
 unsigned int i = 0;
 for(i=0; i<size; i++)
 {
  if(islower(originalMessage[i]))
  {
   codedMessage[i] = (((short)(originalMessage[i]-'a') + shift)
                      %NUMBER_OF_LETTERS) + 'a';
  }
  else if(isupper(originalMessage[i]))
  {
   codedMessage[i] = (((short)(originalMessage[i]-'A') + shift)
                      %NUMBER_OF_LETTERS) + 'A';
  }
  else if(isdigit(originalMessage[i]))
  {
   codedMessage[i] = ((short)(originalMessage[i]-'0') + shift)
                      %NUMBER_OF_DIGITS + '0';
  }
  else if(strchr(CAESAR_CIPHER_SPECIAL_CHARS, originalMessage[i])!=NULL)
  {
   codedMessage[i] = originalMessage[i];
  }
  else
  {
   return OPERATION_FAILED;
  }
 }
 codedMessage[size] = '\0';
 return OPERATION_SUCCESS;
}
2. The Decryption Algorithm
We shall consider E as the encrypted string and O as the decrypted string. O is calculated using the formulas displayed below:

  • Oi - the element at  the i-th position in the decrypted string.
  • Ei - the element at  the i-th position in the encrypted string.
  • M - a predefined set of elements who will not be encypted (this set will be contained in CAESAR_CIPHER_SPECIAL_CHARS).
  • s - how many positions a letter or a digit was shifted
  • The "magic numbers" 97, 65 and 48 represent the ASCII codes of 'a', 'A' and '0', while 26 and 10 represent the number of letters of the English alphabet respectively the number of digits. 
Example (s=3) :
The encrypted string: L DP FDHVDU
The decrypted string: I AM CAESAR

The C implementation:
OPERATION_STATUS CaesarCipher_Decrypt(const char* codedMessage,
                                      char* originalMessage,
                                      short shift)
{
 unsigned int size = strlen(codedMessage);
 unsigned int i = 0;
 for(i=0; i<size; i++)
 {
  if(islower(codedMessage[i]))
  {
   originalMessage[i] = (abs((short)(codedMessage[i]-'a') - shift)
                        %NUMBER_OF_LETTERS) + 'a';
  }
  else if(isupper(codedMessage[i]))
  {
   originalMessage[i] = (abs((short)(codedMessage[i]-'A') - shift)
                        %NUMBER_OF_LETTERS) + 'A';
  }
  else if(isdigit(codedMessage[i]))
  {
   originalMessage[i] = (abs((short)(codedMessage[i]-'0') - shift))
                        %NUMBER_OF_DIGITS + '0';
  }
  else if(strchr(CAESAR_CIPHER_SPECIAL_CHARS, codedMessage[i])!=NULL)
  {
   originalMessage[i] = codedMessage[i];
  }
  else
  {
   return OPERATION_FAILED;
  }
 }
 originalMessage[size] = '\0';
 return OPERATION_SUCCESS;
}
3. Breaking the Caesar's Cipher 
Breaking Caesar's Cipher is not very complicated. For an encrypted string you have NUMBER_OF_LETTERS (normally 26) possible decrypted strings. Using the functions described above it will not be very complicated or time-consuming to generate all strings and figure out the shift value.
char coded[30] = "L dp FDHVDU 5345!!!";
char message[30];
unsigned int i = 0;
for(i=0; i<26;i++)
{
 CaesarCipher_Decrypt(coded,message,i);
 printf("%s with shift value %d\n",message,i);
}
//Output
//L dp FDHVDU 5345!!! with shift value 0
//K co ECGUCT 4234!!! with shift value 1
//J bn DBFTBS 3123!!! with shift value 2
//I am CAESAR 2012!!! with shift value 3
//H bl BBDRBQ 1101!!! with shift value 4
//G ck ACCQCP 0210!!! with shift value 5
//F dj BDBPDO 1321!!! with shift value 6
//E ei CEAOEN 2432!!! with shift value 7
//D fh DFBNFM 3543!!! with shift value 8
//C gg EGCMGL 4654!!! with shift value 9
//B hf FHDLHK 5765!!! with shift value 10
//A ie GIEKIJ 6876!!! with shift value 11
//B jd HJFJJI 7987!!! with shift value 12
//C kc IKGIKH 8098!!! with shift value 13
//D lb JLHHLG 9109!!! with shift value 14
//E ma KMIGMF 0210!!! with shift value 15
//F nb LNJFNE 1321!!! with shift value 16
//G oc MOKEOD 2432!!! with shift value 17
//H pd NPLDPC 3543!!! with shift value 18
//I qe OQMCQB 4654!!! with shift value 19
//J rf PRNBRA 5765!!! with shift value 20
//K sg QSOASB 6876!!! with shift value 21
//L th RTPBTC 7987!!! with shift value 22
//M ui SUQCUD 8098!!! with shift value 23
//N vj TVRDVE 9109!!! with shift value 24
//O wk UWSEWF 0210!!! with shift value 25
By studying the output and using your common sense, you can easily observe that the only sentence that makes sense is the one where the shift value is equal to 3.

Download source here
Related Posts Plugin for WordPress, Blogger...