Caeser Cipher

Discussion in 'Programming' started by iMatt, Dec 9, 2007.

Remove these ads by signing in
Remove these ads by signing in
Thread Status:
Not open for further replies.
  1. iMatt New Member

    Member Since:
    Nov 11, 2007
    Message Count:
    50
    Likes Received:
    0
    Occupation:
    Student
    Location:
    Manchester, UK
    Working Example: Click Here

    This tutorial will go through the basics of encryption by explaining how to make a Caesar Cipher. A cyclic encryption that takes a message and shifts the value of each character depending on the offset key specified. This tutorial is advanced PHP.

    With a key value of 3, the message "The quick brown fox" becomes "wkh txlfn eurzq ira"

    This script uses two functions 'crypto' and 'decrypto' both with two constructor values, the offset key and the message. See the code below:

    PHP:
    <?php
    function crypto($key,$string)
    {
        $letters = array('a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z');
        for($i = 0; $i < strlen($string); $i++)
        {
            switch($string[$i])
            {
                case 'a' : $string[$i] = $letters[((0+$key)%26)]; break;
                case 'b' : $string[$i] = $letters[((1+$key)%26)]; break;
                case 'c' : $string[$i] = $letters[((2+$key)%26)]; break;
                case 'd' : $string[$i] = $letters[((3+$key)%26)]; break;
                case 'e' : $string[$i] = $letters[((4+$key)%26)]; break;
                case 'f' : $string[$i] = $letters[((5+$key)%26)]; break;
                case 'g' : $string[$i] = $letters[((6+$key)%26)]; break;
                case 'h' : $string[$i] = $letters[((7+$key)%26)]; break;
                case 'i' : $string[$i] = $letters[((8+$key)%26)]; break;
                case 'j' : $string[$i] = $letters[((9+$key)%26)]; break;
                case 'k' : $string[$i] = $letters[((10+$key)%26)]; break;
                case 'l' : $string[$i] = $letters[((11+$key)%26)]; break;
                case 'm' : $string[$i] = $letters[((12+$key)%26)]; break;
                case 'n' : $string[$i] = $letters[((13+$key)%26)]; break;
                case 'o' : $string[$i] = $letters[((14+$key)%26)]; break;
                case 'p' : $string[$i] = $letters[((15+$key)%26)]; break;
                case 'q' : $string[$i] = $letters[((16+$key)%26)]; break;
                case 'r' : $string[$i] = $letters[((17+$key)%26)]; break;
                case 's' : $string[$i] = $letters[((18+$key)%26)]; break;
                case 't' : $string[$i] = $letters[((19+$key)%26)]; break;
                case 'u' : $string[$i] = $letters[((20+$key)%26)]; break;
                case 'v' : $string[$i] = $letters[((21+$key)%26)]; break;
                case 'w' : $string[$i] = $letters[((22+$key)%26)]; break;
                case 'x' : $string[$i] = $letters[((23+$key)%26)]; break;
                case 'y' : $string[$i] = $letters[((24+$key)%26)]; break;
                case 'z' : $string[$i] = $letters[((25+$key)%26)]; break;
                default: $string[$i] = $string[$i];
            }
        }
        return $string;
    }

    function decrypto($key,$string)
    {
        $letters = array('a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z');
        for($i = 0; $i < strlen($string); $i++)
        {
            switch($string[$i])
            {
                case 'a' : $string[$i] = $letters[abs((($key-0-26)%26))]; break;
                case 'b' : $string[$i] = $letters[abs((($key-1-26)%26))]; break;
                case 'c' : $string[$i] = $letters[abs((($key-2-26)%26))]; break;
                case 'd' : $string[$i] = $letters[abs((($key-3-26)%26))]; break;
                case 'e' : $string[$i] = $letters[abs((($key-4-26)%26))]; break;
                case 'f' : $string[$i] = $letters[abs((($key-5-26)%26))]; break;
                case 'g' : $string[$i] = $letters[abs((($key-6-26)%26))]; break;
                case 'h' : $string[$i] = $letters[abs((($key-7-26)%26))]; break;
                case 'i' : $string[$i] = $letters[abs((($key-8-26)%26))]; break;
                case 'j' : $string[$i] = $letters[abs((($key-9-26)%26))]; break;
                case 'k' : $string[$i] = $letters[abs((($key-10-26)%26))]; break;
                case 'l' : $string[$i] = $letters[abs((($key-11-26)%26))]; break;
                case 'm' : $string[$i] = $letters[abs((($key-12-26)%26))]; break;
                case 'n' : $string[$i] = $letters[abs((($key-13-26)%26))]; break;
                case 'o' : $string[$i] = $letters[abs((($key-14-26)%26))]; break;
                case 'p' : $string[$i] = $letters[abs((($key-15-26)%26))]; break;
                case 'q' : $string[$i] = $letters[abs((($key-16-26)%26))]; break;
                case 'r' : $string[$i] = $letters[abs((($key-17-26)%26))]; break;
                case 's' : $string[$i] = $letters[abs((($key-18-26)%26))]; break;
                case 't' : $string[$i] = $letters[abs((($key-19-26)%26))]; break;
                case 'u' : $string[$i] = $letters[abs((($key-20-26)%26))]; break;
                case 'v' : $string[$i] = $letters[abs((($key-21-26)%26))]; break;
                case 'w' : $string[$i] = $letters[abs((($key-22-26)%26))]; break;
                case 'x' : $string[$i] = $letters[abs((($key-23-26)%26))]; break;
                case 'y' : $string[$i] = $letters[abs((($key-24-26)%26))]; break;
                case 'z' : $string[$i] = $letters[abs((($key-25-26)%26))]; break;
                default: $string[$i] = $string[$i];
            }
        }
        return $string;
    }

    ?>
    The crypo function encrypts the message. This is what it does:

    * Loads all the letters a-z into an array.
    * Uses a for loop to scan through the message and filters it with a switch statement.
    * Shifts the value of the character at $string[$i]
    * Returns the encrypted message when the loop has finished.

    Inside the for loop there is a switch statement that takes the character at $string[$i] and filters it through the possible cases. If it finds one it will do the following:
    case 'b' : $string[$i] = $letters[((1+$key)%26)]; break;

    Once it finds the letter 'b' in the string it will update the value of $string[$i]. It uses the $letters array to find the correct value. If my offset key was four this is what it would be returned:

    $letters[((1+4)%26)]; = $letters[(5 % 26)] = $letters[5] = 'f'

    So 'b' pushed up four spots is 'f'. The reason I am using modular division is to prevent an array out of bounds exception, or searching in the array at an index that doesn't exist, in php this doesn't throw an error but doesn't return anything either. An example of this would be the letter 'x' with an offset key of four.
    case 'x' : $string[$i] = $letters[((23+4))]; break;

    Without mod 26(the number of letters in the alphabet) this would look for $letters[27], which doesn't exist. However, with it, 27 % 26 = 1 and $letters[1] is 'b'.

    The decrypto function is very similar but has some big differences. Mainly its switch cases.
    case 'a' : $string[$i] = $letters[abs((($key-0-26)%26))]; break;

    With a key of four this would return:
    abs(((4-0-26)%26)) = abs(-22 % 26) = 22 = 'w'

    The -26 is in there to make sure that it gets to the right value. Without it (4%26) would be 'e'. That is going four steps up, not four steps back. I'm using the abs(absolute value function) for higher letters to keep the index value positive.

    Take 'y' for example:
    case 'y' : $string[$i] = $letters[abs((($key-24-26)%26))]; break;

    4-24-26 = -46 % 26 = -20, this doesn't exist in the array but 20 does and it is the correct value.

    Now on to the forms that make the script work. See the code below:
    PHP:
    <table width="100%" border="0" cellspacing="0" cellpadding="0">
      <tr>
        <td><form id="encrypt" name="encrypt" method="post" action="">
      Offset Key
      (1-25)
        <input name="key" type="text" id="key" />
      <br />
      <textarea name="encrypt" cols="35" rows="15" id="encrypt"><?php
    if(isset($_POST['decrypt']) && $_POST['key'] >=1 && $_POST['key'] <= 25)
        echo decrypto($_POST['key'],strtolower($_POST['decrypt']));
    ?></textarea>
      <br />
      <input type="submit" name="Submit" value="Encrypt This Message" />
      <br />
    </form></td>
        <td><form id="decrypt" name="decrypt" method="post" action="">
      Offset Key
      (1-25)
        <input name="key" type="text" id="key" />
      <br />
      <textarea name="decrypt" cols="35" rows="15" id="decrypt"><?php
    if(isset($_POST['encrypt']) && $_POST['key'] >=1 && $_POST['key'] <= 25)
        echo crypto($_POST['key'],strtolower($_POST['encrypt']));
    ?></textarea>
      <br />
      <input type="submit" name="Submit" value="Decrypt This Message" />
      <br />
    </form></td>
      </tr>
    </table>
    This code creates two forms, one for encryption and the other for decryption. It will only allow numbers from 1-25, a key of 0 or 26 do nothing.

    Inside each textarea there is code similar to this:

    if(isset($_POST['decrypt']) && $_POST['key'] >=1 & $_POST['key'] <= 25)
    echo decrypto($_POST['key'],strtolower($_POST['decrypt']));
    ?>

    This checks if the opposite form has been submitted and that the correct values are in the key field. If both are true then it will set the case of the message to lowercase and send it through the function and out comes your encrypted or decrypted message.

    Here is the full code:
    PHP:
    <?php
    function crypto($key,$string)
    {
        $letters = array('a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z');
        for($i = 0; $i < strlen($string); $i++)
        {
            switch($string[$i])
            {
                case 'a' : $string[$i] = $letters[((0+$key)%26)]; break;
                case 'b' : $string[$i] = $letters[((1+$key)%26)]; break;
                case 'c' : $string[$i] = $letters[((2+$key)%26)]; break;
                case 'd' : $string[$i] = $letters[((3+$key)%26)]; break;
                case 'e' : $string[$i] = $letters[((4+$key)%26)]; break;
                case 'f' : $string[$i] = $letters[((5+$key)%26)]; break;
                case 'g' : $string[$i] = $letters[((6+$key)%26)]; break;
                case 'h' : $string[$i] = $letters[((7+$key)%26)]; break;
                case 'i' : $string[$i] = $letters[((8+$key)%26)]; break;
                case 'j' : $string[$i] = $letters[((9+$key)%26)]; break;
                case 'k' : $string[$i] = $letters[((10+$key)%26)]; break;
                case 'l' : $string[$i] = $letters[((11+$key)%26)]; break;
                case 'm' : $string[$i] = $letters[((12+$key)%26)]; break;
                case 'n' : $string[$i] = $letters[((13+$key)%26)]; break;
                case 'o' : $string[$i] = $letters[((14+$key)%26)]; break;
                case 'p' : $string[$i] = $letters[((15+$key)%26)]; break;
                case 'q' : $string[$i] = $letters[((16+$key)%26)]; break;
                case 'r' : $string[$i] = $letters[((17+$key)%26)]; break;
                case 's' : $string[$i] = $letters[((18+$key)%26)]; break;
                case 't' : $string[$i] = $letters[((19+$key)%26)]; break;
                case 'u' : $string[$i] = $letters[((20+$key)%26)]; break;
                case 'v' : $string[$i] = $letters[((21+$key)%26)]; break;
                case 'w' : $string[$i] = $letters[((22+$key)%26)]; break;
                case 'x' : $string[$i] = $letters[((23+$key)%26)]; break;
                case 'y' : $string[$i] = $letters[((24+$key)%26)]; break;
                case 'z' : $string[$i] = $letters[((25+$key)%26)]; break;
                default: $string[$i] = $string[$i];
            }
        }
        return $string;
    }

    function decrypto($key,$string)
    {
        $letters = array('a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z');
        for($i = 0; $i < strlen($string); $i++)
        {
            switch($string[$i])
            {
                case 'a' : $string[$i] = $letters[abs((($key-0-26)%26))]; break;
                case 'b' : $string[$i] = $letters[abs((($key-1-26)%26))]; break;
                case 'c' : $string[$i] = $letters[abs((($key-2-26)%26))]; break;
                case 'd' : $string[$i] = $letters[abs((($key-3-26)%26))]; break;
                case 'e' : $string[$i] = $letters[abs((($key-4-26)%26))]; break;
                case 'f' : $string[$i] = $letters[abs((($key-5-26)%26))]; break;
                case 'g' : $string[$i] = $letters[abs((($key-6-26)%26))]; break;
                case 'h' : $string[$i] = $letters[abs((($key-7-26)%26))]; break;
                case 'i' : $string[$i] = $letters[abs((($key-8-26)%26))]; break;
                case 'j' : $string[$i] = $letters[abs((($key-9-26)%26))]; break;
                case 'k' : $string[$i] = $letters[abs((($key-10-26)%26))]; break;
                case 'l' : $string[$i] = $letters[abs((($key-11-26)%26))]; break;
                case 'm' : $string[$i] = $letters[abs((($key-12-26)%26))]; break;
                case 'n' : $string[$i] = $letters[abs((($key-13-26)%26))]; break;
                case 'o' : $string[$i] = $letters[abs((($key-14-26)%26))]; break;
                case 'p' : $string[$i] = $letters[abs((($key-15-26)%26))]; break;
                case 'q' : $string[$i] = $letters[abs((($key-16-26)%26))]; break;
                case 'r' : $string[$i] = $letters[abs((($key-17-26)%26))]; break;
                case 's' : $string[$i] = $letters[abs((($key-18-26)%26))]; break;
                case 't' : $string[$i] = $letters[abs((($key-19-26)%26))]; break;
                case 'u' : $string[$i] = $letters[abs((($key-20-26)%26))]; break;
                case 'v' : $string[$i] = $letters[abs((($key-21-26)%26))]; break;
                case 'w' : $string[$i] = $letters[abs((($key-22-26)%26))]; break;
                case 'x' : $string[$i] = $letters[abs((($key-23-26)%26))]; break;
                case 'y' : $string[$i] = $letters[abs((($key-24-26)%26))]; break;
                case 'z' : $string[$i] = $letters[abs((($key-25-26)%26))]; break;
                default: $string[$i] = $string[$i];
            }
        }
        return $string;
    }

    ?>

    <table width="100%" border="0" cellspacing="0" cellpadding="0">
      <tr>
        <td><form id="encrypt" name="encrypt" method="post" action="">
      Offset Key
      (1-25)
        <input name="key" type="text" id="key" />
      <br />
      <textarea name="encrypt" cols="35" rows="15" id="encrypt"><?php
    if(isset($_POST['decrypt']) && $_POST['key'] >=1 & $_POST['key'] <= 25)
        echo decrypto($_POST['key'],strtolower($_POST['decrypt']));
    ?></textarea>
      <br />
      <input type="submit" name="Submit" value="Encrypt This Message" />
      <br />
    </form></td>
        <td><form id="decrypt" name="decrypt" method="post" action="">
      Offset Key
      (1-25)
        <input name="key" type="text" id="key" />
      <br />
      <textarea name="decrypt" cols="35" rows="15" id="decrypt"><?php
    if(isset($_POST['encrypt']) && $_POST['key'] >=1 & $_POST['key'] <= 25)
        echo crypto($_POST['key'],strtolower($_POST['encrypt']));
    ?></textarea>
      <br />
      <input type="submit" name="Submit" value="Decrypt This Message" />
      <br />
    </form></td>
      </tr>
    </table>
    Please add reputation if you liked this tutorial.
    Copyright Admin Utopia (c) 2007
  2. ALEX New Member

    Member Since:
    Sep 6, 2007
    Message Count:
    524
    Likes Received:
    0
    Very nice Matt.

    orawb ihcwo fizsg
  3. iMatt New Member

    Member Since:
    Nov 11, 2007
    Message Count:
    50
    Likes Received:
    0
    Occupation:
    Student
    Location:
    Manchester, UK
    I need the offset key to decrypt your message. This was how the Romans used to send confidential messages, they would leave a number at the top of the page, and then write their message using the offset number, then the person receiving it would know to go backwards by the amount set. Henceforth the name, Caesers Ciphor.
  4. Hayze New Member

    Member Since:
    Sep 6, 2007
    Message Count:
    949
    Likes Received:
    0
    Occupation:
    Un Occupied.
    Location:
    To your left... no your other left.
    Wow, very complicated code, but very useful, well written iMatt!
  5. iMatt New Member

    Member Since:
    Nov 11, 2007
    Message Count:
    50
    Likes Received:
    0
    Occupation:
    Student
    Location:
    Manchester, UK
    Cheers Bill, once I got my head around moving letters via an offset key, it was quite simple to be honest.
  6. Eureka New Member

    Member Since:
    Dec 16, 2007
    Message Count:
    17
    Likes Received:
    0
    o_O Really!? I really doubt they write down the key on a piece of parchment. That's not confidential. I'm sure they just gather together before the mission and just tell a certain person.
  7. Edwin New Member

    Member Since:
    Oct 7, 2007
    Message Count:
    417
    Likes Received:
    0
    Occupation:
    Now that would be telling
    Location:
    UK
    No, only the person decrypting the message (the rightful person) knew how to use the key.

    The key is useless if you can't use the algorithm
  8. Eureka New Member

    Member Since:
    Dec 16, 2007
    Message Count:
    17
    Likes Received:
    0
    Nope, once the key is gotten, the message can be decrypted quite easily. Back then, while they still don't have computers, the numbers they use I imagine won't be too big. I think at first, Caesar just used a off-key to add onto the number 26 and use modulo arithmetic. Later it will become to multiplication. As of now, things like RSA uses exponentials; however, without a computer, that's frankly hard to calculate.
  9. Edwin New Member

    Member Since:
    Oct 7, 2007
    Message Count:
    417
    Likes Received:
    0
    Occupation:
    Now that would be telling
    Location:
    UK
    You misunderstand me, it didn't matter that the key was known because only the person receiving the message knew the actual algorithm

    It doesn't matter that you know the key if its just a random number that you have no idea how to use.

    Only the recipient knew how to decode the message when he had the key
  10. iMatt New Member

    Member Since:
    Nov 11, 2007
    Message Count:
    50
    Likes Received:
    0
    Occupation:
    Student
    Location:
    Manchester, UK
    Hi Eureka,

    Only the people that knew about Caeser Ciphor, and it was very few, would be able to understand how to decrypt the message. Consider yourself in a scenario as a Saxon, you intercept a Roman message with letters in what seem to the naked eye as randomly put together, you also see a number, but because you aren't Roman, you are completely baffled. Therefore, you could not decrypt the message. At the time, it was very advanced encrypting.

    (Thanks for the congratulations in your signature Edwin!)
  11. Edwin New Member

    Member Since:
    Oct 7, 2007
    Message Count:
    417
    Likes Received:
    0
    Occupation:
    Now that would be telling
    Location:
    UK
    No problem, thanks for explaining exactly what I said in words that are understandable to other human beings :D
  12. iMatt New Member

    Member Since:
    Nov 11, 2007
    Message Count:
    50
    Likes Received:
    0
    Occupation:
    Student
    Location:
    Manchester, UK
    :p I just try to help people consider what it would be like if you were in the situation, that way, its easier for them to understand :D
  13. Eureka New Member

    Member Since:
    Dec 16, 2007
    Message Count:
    17
    Likes Received:
    0
    iMatt, I agree with you that Caesar's success was based on this system; however, it's not a mystery that lasted a long time. What I was asking was: "Do they really WRITE the key on the parchment?" I mean if the messenger was intercepted, it would be easy to decode after a few times. Humans aren't that stupid, even back then. :p

    Appreciate the efforts iMatt and Edwin, but I just don't think they answer my question.
  14. iMatt New Member

    Member Since:
    Nov 11, 2007
    Message Count:
    50
    Likes Received:
    0
    Occupation:
    Student
    Location:
    Manchester, UK
    Ok, well, the key would have been different every time, meaning that each message would be decoded differently, so it would be difficult to find a pattern in decoding the message correctly each time. You are right, after some time the encryption method was found out, and was made obsolete. But this is like most encryption methods, after a certain amount of time, the method becomes unsafe to use.


    I hope I have answered your question well enough.
  15. Eureka New Member

    Member Since:
    Dec 16, 2007
    Message Count:
    17
    Likes Received:
    0
    Thank you v.v
Thread Status:
Not open for further replies.

Share This Page