StackOverflowNewbie
StackOverflowNewbie

Reputation: 40633

Safe Encrypt/Decrypt Functions

Given an input string (will actually be an integer value) and an encryption key, I need to encrypt the input string in such a way that the resulting string is:

  1. URL safe (my permitted URI characters is currently: a-z 0-9~%.:_-)
  2. Filename safe (meaning, it only uses valid directory/filename characters)
  3. FTP account username safe
  4. Email account username safe

Then, given the encrypted string and the same encryption key, decrypt the the string into its unencrypted form.

This is not intended to be a security measure. Implementation needs to be in PHP. Thanks.

EDIT 1 (the decoding still includes undesirable characters; plus, there is no way to make sure the resulting encrypted string is within a certain length):

function decrypt($string, $encryption_key)
{
    assert(isset($string) === TRUE);
    assert(isset($encryption_key) === TRUE);

    $result = '';
    $string = base64_decode($string);

    for ($i = 0; $i < strlen($string); $i++)
    {
        $char    = substr($string, $i, 1);
        $keychar = substr($encryption_key, ($i % strlen($encryption_key)) - 1, 1);
        $char    = chr(ord($char) - ord($keychar));
        $result .= $char;
    }

    return $result;
}


function encrypt($string, $encryption_key)
{
    assert(isset($string) === TRUE);
    assert(isset($encryption_key) === TRUE);

    $string = (string) $string;
    $result = '';

    for ($i = 0; $i < strlen($string); $i++)
    {
        $char    = substr($string, $i, 1);
        $keychar = substr($encryption_key, ($i % strlen($encryption_key)) - 1, 1);
        $char    = chr(ord($char) + ord($keychar));
        $result .= $char;
    }

    return base64_encode($result);
}

Upvotes: 0

Views: 2074

Answers (2)

James Black
James Black

Reputation: 41858

For encrypting, depending on your security demands, the mcrypt_encrypt (https://www.php.net/manual/en/function.mcrypt-encrypt.php) functions may be simple enough.

Once you get it working, then, if you need more security you can change the encryption function as the rest of your program won't care.

Once you encrypt you can use base-64 encoding (https://www.php.net/manual/en/function.base64-encode.php), which is a known pattern that is well-tested.

Since you are encrypting an int, which is at most 8 bytes long, any length of key should be fine, in order to have a known size result your key needs to >= 8 bytes.

I would suggest you don't write your own encryption algorithm, as it will be insecure, and there are many out there to meet your needs, depending on whatever other requirements you have. As was mentioned, you can work back and determine the size that you want the encoded string to be, that will tell you how many bytes the encrypted result can be. Then, you can work out the size of the key in order to get the size of the encrypted message.

If you want to encrypt a string of arbitrary length, then the previous paragraph will be wrong, as the size of the encrypted message won't be known.

Upvotes: 1

President James K. Polk
President James K. Polk

Reputation: 41967

Consider encryption and encoding as two distinct and unrelated steps. In one direction you encrypt plaintext bytes to get cipher bytes, then encode the bytes to get a string. The other direction you decode the string to get ciphertext bytes, then decrypt the ciphertext bytes to get plaintext bytes.

Your requirements can be most simply satisfied by using a simple hex, or base 16, encoder that converts a byte into two hex characters. If encoding space efficiency is absolutely critical, you can implement your own base-62 encoder that uses only upper and lower case letters and digits. It will be slower and possibly uglier than hex encoding.

EDIT 1:

If base-64 encoding produces acceptable strings all the better. Base-64 uses 4 characters to encode 3 bytes. So if you are limited to 64 characters then you cannot encode more than (64/4) * 3 = 48 bytes.

Upvotes: 1

Related Questions