When I encrypt with C# I get arTdPqWOg6VppOqUD6mGITjb24+x5vJjfAufNQ4DN7rVEtpDmhFnMeJGg4n5y1BN
static void Main(string[] args)
{
Encoding byteEncoder = Encoding.Default;
String key = "ShHhd8a08JhJiho98ayslcjh";
String message = "Let us meet at 9 o'clock at the secret place.";
String encryption = Encrypt(message, key, false);
String decryption = Decrypt(encryption , key, false);
Console.WriteLine("Message: {0}", message);
Console.WriteLine("Encryption: {0}", encryption);
Console.WriteLine("Decryption: {0}", decryption);
}
public static string Encrypt(string toEncrypt, string key, bool useHashing)
{
byte[] keyArray;
byte[] toEncryptArray = UTF8Encoding.UTF8.GetBytes(toEncrypt);
if (useHashing)
{
MD5CryptoServiceProvider hashmd5 = new MD5CryptoServiceProvider();
keyArray = hashmd5.ComputeHash(UTF8Encoding.UTF8.GetBytes(key));
}
else
keyArray = UTF8Encoding.UTF8.GetBytes(key);
TripleDESCryptoServiceProvider tdes = new TripleDESCryptoServiceProvider();
tdes.Key = keyArray;
tdes.Mode = CipherMode.ECB;
tdes.Padding = PaddingMode.PKCS7;
ICryptoTransform cTransform = tdes.CreateEncryptor();
byte[] resultArray = cTransform.TransformFinalBlock(toEncryptArray, 0, toEncryptArray.Length);
return Convert.ToBase64String(resultArray, 0, resultArray.Length);
}
public static string Decrypt(string toDecrypt, string key, bool useHashing)
{
byte[] keyArray;
byte[] toEncryptArray = Convert.FromBase64String(toDecrypt);
if (useHashing)
{
MD5CryptoServiceProvider hashmd5 = new MD5CryptoServiceProvider();
keyArray = hashmd5.ComputeHash(UTF8Encoding.UTF8.GetBytes(key));
}
else
keyArray = UTF8Encoding.UTF8.GetBytes(key);
TripleDESCryptoServiceProvider tdes = new TripleDESCryptoServiceProvider();
tdes.Key = keyArray;
tdes.Mode = CipherMode.ECB;
tdes.Padding = PaddingMode.PKCS7;
ICryptoTransform cTransform = tdes.CreateDecryptor();
byte[] resultArray = cTransform.TransformFinalBlock(toEncryptArray, 0, toEncryptArray.Length);
return UTF8Encoding.UTF8.GetString(resultArray);
}
When I encrypt with PHP I get: arTdPqWOg6VppOqUD6mGITjb24+x5vJjfAufNQ4DN7rVEtpDmhFnMVM+W/WFlksR
<?php
$key = "ShHhd8a08JhJiho98ayslcjh";
$input = "Let us meet at 9 o'clock at the secret place.";
$td = mcrypt_module_open('tripledes', '', 'ecb', '');
$iv = mcrypt_create_iv (mcrypt_enc_get_iv_size($td), MCRYPT_RAND);
mcrypt_generic_init($td, $key, $iv);
$encrypted_data = mcrypt_generic($td, $input);
mcrypt_generic_deinit($td);
mcrypt_module_close($td);
echo base64_encode($encrypted_data);
?>
I don't know enough about cryptography to figure out why. Any ideas? Thanks.
Peter is right. PHP just pads with zeros, while you're using PKCS#7 in the C# code. Here's some code that should do it right:
function pkcs7_pad($text, $blocksize)
{
$pad = $blocksize - (strlen($text) % $blocksize);
return $text . str_repeat(chr($pad), $pad);
}
$input = pkcs7_pad("Let us meet at 9 o'clock at the secret place.", 16);
Alternatively, you should be able to put this in your C# code:
tdes.Padding = PaddingMode.Zeros;
and also have it work (albeit slightly less securely).
I don't know PHP, and neither have I analysed your C# code carefully, but as most of the encrypted string is the same maybe the padding of the data is the difference? Maybe PHP uses another mode than the PaddingMode.PKCS7 used in the C# code? (This would have been a comment if I could comment...)
As a side note: if you are using ECB then you do not need an IV. Actually, using ECB is most of the time a security hazard, so you really need to use something else, e.g. CBC, which uses an IV. The IV is a random, non-secret value with the same size than the cipher block size (8 bytes for 3DES). A new IV must be created for each message, and the decrypting party must know the IV that the encrypting party used. In practice, the IV is sent along with the encrypted message.
Related
I have a sample code in .NET C# which I need to convert to RUBY.
public static string Encrypt(string pstrText)
{
byte[] keyArray;
byte[] toEncryptArray = UTF8Encoding.UTF8.GetBytes(pstrText);
MD5CryptoServiceProvider hashmd5 = new MD5CryptoServiceProvider();
keyArray = hashmd5.ComputeHash(UTF8Encoding.UTF8.GetBytes(secKey));
hashmd5.Clear();
TripleDESCryptoServiceProvider tdes = new TripleDESCryptoServiceProvider();
tdes.Key = keyArray;
tdes.Mode = CipherMode.ECB;
tdes.Padding = PaddingMode.PKCS7;
ICryptoTransform cTransform = tdes.CreateEncryptor();
byte[] resultArray =cTransform.TransformFinalBlock(toEncryptArray, 0, toEncryptArray.Length);
tdes.Clear();
return Convert.ToBase64String(resultArray, 0, resultArray.Length);
}
I have tried using OPENSSL:CIPHER and got thus far -
def encrypt data
secret = "******************"
md5 = Digest::MD5.hexdigest(secret)
des = OpenSSL::Cipher::Cipher.new 'DES-EDE3'
des.encrypt
des.key = md5
update_value = des.update(data)
up_final = update_value + des.final
puts Base64.encode64(up_final).gsub(/\n/, "")
end
The results in C# and RUBY do not match. Where am I going wrong?
I have a service named CryptoService which inherit the interface ICryptoService that consist of 2 method Crypto Decrypto function.
Encryption of a string is Working but the Decryption of hash result will return my key instead of the Decrypted string.
Here is my encryption code :
private string _salt = "*1234567890!##$%^&*()14344*";
private string Crypto(string text)
{
var hashmd5 = new MD5CryptoServiceProvider();
byte[] toEncryptArray = Encoding.UTF8.GetBytes(_salt);
byte[] keyArray = hashmd5.ComputeHash(Encoding.UTF8.GetBytes(_salt));
hashmd5.Clear();
TripleDesProvider.Key = keyArray;
TripleDesProvider.Mode = CipherMode.ECB;
TripleDesProvider.Padding = PaddingMode.PKCS7;
ICryptoTransform cTransform = TripleDesProvider.CreateEncryptor();
byte[] resultArray = cTransform.TransformFinalBlock(toEncryptArray, 0, toEncryptArray.Length);
return Convert.ToBase64String(resultArray, 0, resultArray.Length);
}
My decryption code :
private string Decrypto(string text)
{
try
{
var hashmd5 = new MD5CryptoServiceProvider();
byte[] toEncryptArray = Convert.FromBase64String(text);
byte[] keyArray = hashmd5.ComputeHash(Encoding.UTF8.GetBytes(_salt));
hashmd5.Clear();
TripleDesProvider.Key = keyArray;
TripleDesProvider.Mode = CipherMode.ECB;
TripleDesProvider.Padding = PaddingMode.PKCS7;
ICryptoTransform cTransform = TripleDesProvider.CreateDecryptor();
byte[] resultArray = cTransform.TransformFinalBlock(toEncryptArray, 0, toEncryptArray.Length);
TripleDesProvider.Clear();
return Encoding.UTF8.GetString(resultArray);
//return Encoding.UTF8.GetString(resultArray);
}
catch
{
return string.Empty;
}
}
provided here the screenshot in action.
here are the references of my codes I found in the internet
https://www.codeproject.com/Articles/14150/Encrypt-and-Decrypt-Data-with-C
This cannot work. A hash, such as MD5, is one-way. You cannot get the original text from the hash value.
If your crypto service runs on the same machine, I suggest using the Data Protection class.
Your toEncryptArray in Encrypto gets the value _salt. You meant text.
So, good news, your decryption works.
I am decrypting a message in C#, this message is encrypted in PHP using below code:-
public function __construct($sEncryptionKey)
{
$this->link = mcrypt_module_open('tripledes', '', 'ecb', '');
$this->sInitializationVector = mcrypt_create_iv(mcrypt_enc_get_iv_size($this->link), MCRYPT_RAND);
$this->iKeySize = mcrypt_enc_get_key_size($this->link);
$sEncryptionKey = substr(md5($sEncryptionKey), 0, $this->iKeySize);
mcrypt_generic_init($this->link, $sEncryptionKey, $this->sInitializationVector);
}
public function encrypt($sDataToEncrypt)
{
return base64_encode(mcrypt_generic($this->link, $sDataToEncrypt));
}
And I am using below decryption function in c# for decryption:-
public string Decrypt(string toDecrypt, string key, bool useHashing)
{
byte[] keyArray;
byte[] toEncryptArray = Convert.FromBase64String(toDecrypt);
if (useHashing)
{
MD5CryptoServiceProvider hashmd5 = new MD5CryptoServiceProvider();
keyArray = hashmd5.ComputeHash(UTF8Encoding.UTF8.GetBytes(key));
hashmd5.Clear();
}
else
{
keyArray = UTF8Encoding.UTF8.GetBytes(key);
}
TripleDESCryptoServiceProvider tdes = new TripleDESCryptoServiceProvider();
tdes.Key = keyArray;
tdes.Mode = CipherMode.ECB;
tdes.Padding = PaddingMode.Zeros;
ICryptoTransform cTransform = tdes.CreateDecryptor();
byte[] resultArray = cTransform.TransformFinalBlock(toEncryptArray, 0, toEncryptArray.Length);
tdes.Clear();
var strValue = UTF8Encoding.UTF8.GetString(resultArray);
return UTF8Encoding.UTF8.GetString(resultArray);
}
I tried with few changes and getting below results:-
1.) PaddingMode.PKCS7 with no hashing = "Specified key is not a valid size for this algorithm."
2.) PaddingMode.PKCS7 with hashing = "Bad Data."
3.) PaddingMode.Zeros with no hashing = "Specified key is not a valid size for this algorithm."
4.) PaddingMode.Zeros with hashing = "�8�f����q6IGs�" some unknown characters
I think 4'th one will work, but not sure what I am doing wrong.
Found a solution, need to do changes in MD5 hashing, below are whole code if someone stuck in same situation :-
public string Decrypt(string toDecrypt, string key, bool useHashing)
{
TripleDESCryptoServiceProvider tdes = new TripleDESCryptoServiceProvider();
byte[] keyArray;
byte[] toEncryptArray = Convert.FromBase64String(toDecrypt);
string keyArrayStr = "";
if (useHashing)
{
MD5 md5 = MD5CryptoServiceProvider.Create();
byte[] dataMd5 = md5.ComputeHash(Encoding.Default.GetBytes(key));
StringBuilder sb = new StringBuilder();
for (int i = 0; i < dataMd5.Length; i++)
sb.AppendFormat("{0:x2}", dataMd5[i]);
keyArrayStr = sb.ToString().Substring(0, tdes.Key.Length);
keyArray = UTF8Encoding.UTF8.GetBytes(keyArrayStr);
}
else
{
keyArray = UTF8Encoding.UTF8.GetBytes(key);
}
tdes.Key = keyArray;
tdes.Mode = CipherMode.ECB;
tdes.Padding = PaddingMode.Zeros;
ICryptoTransform cTransform = tdes.CreateDecryptor();
byte[] resultArray = cTransform.TransformFinalBlock(toEncryptArray, 0, toEncryptArray.Length);
tdes.Clear();
var strValue = UTF8Encoding.UTF8.GetString(resultArray);
return UTF8Encoding.UTF8.GetString(resultArray);
}
I am trying to understand and implement 3DES Encryption using C# that would be compatible with oracle dbms_obfuscation_toolkit.
I got help from below two location
https://javasight.wordpress.com/2008/08/24/net-encryption-and-oracle-decryption/
Different DES Encryption in Oracle and .NET
Unfortunately I'm unable to create an encrypted string compatible with below statement
select trim(dbms_obfuscation_toolkit.DESDecrypt(input_string=>utl_raw.cast_to_varchar2(hextoraw('EncryptedString')),key_string=>'MagicKey'))
from dual
public static string Encrypt(string toEncrypt)
{
byte[] keyArray;
byte[] toEncryptArray = UTF8Encoding.UTF8.GetBytes(toEncrypt);
string iv = "0123456789ABCDEF";
string s = "4D616769634B6579";
keyArray = ASCIIEncoding.ASCII.GetBytes(s);
byte[] ivBytes = new byte[iv.Length];
ivBytes = StringUtilities.HexStringToByteArray(iv);
TripleDESCryptoServiceProvider tdes = new TripleDESCryptoServiceProvider();
tdes.Key = keyArray;
tdes.IV = ivBytes;
tdes.Padding = PaddingMode.None;
ICryptoTransform cTransform = tdes.CreateEncryptor();
byte[] resultArray = cTransform.TransformFinalBlock
(toEncryptArray, 0, toEncryptArray.Length);
tdes.Clear();
return StringUtilities.ByteArrayToHexString(resultArray);
}
The key that I am using in C# Code is rawtohex('MagicKey') which translates to 4D616769634B6579
I have an encrypted database in which the strings are values like the below:
ùœ¢Qa³•ù¼?-pJ´’ˆò»Æ8-skYIÞµ§¬†Œ‚„Šç
ù¢=~Òñ€Ï?-pJ´’ˆò»Æ8-skYIÞµ§¬†Œ‚„Šç
XwÚûùÖP^opJ´’ˆò»Æ8-skYIÞµ§¬†Œ‚„Šç
ö‘±_|Çúùß^_f9´’ˆò»Æ8-skYIÞµ§¬†Œ‚„Šç
I'm trying different ways to dencrypt the information (it's a simmetric encryption and I have the key, but I don't know the algorithm, more detail here How to decrypt a string encrypted by V FoxPro)
When I tried different ways to dencrypt using C#.NET in an step I get àn error saying that "the string has a non-base64 character" in the following line:
Convert.FromBase64String(input)
Where input is a string similar to the one I share above.
How Can I receive an string like that from DB in order to work with that in C#?
I normally use something like this:
public static class EncryptDecryptString
{
public static string Encrypt(string input, string key)
{
byte[] inputArray = UTF8Encoding.UTF8.GetBytes(input);
TripleDESCryptoServiceProvider tripleDES = new TripleDESCryptoServiceProvider();
tripleDES.Key = UTF8Encoding.UTF8.GetBytes(key);
tripleDES.Mode = CipherMode.ECB;
tripleDES.Padding = PaddingMode.PKCS7;
ICryptoTransform cTransform = tripleDES.CreateEncryptor();
byte[] resultArray = cTransform.TransformFinalBlock(inputArray, 0, inputArray.Length);
tripleDES.Clear();
return Convert.ToBase64String(resultArray, 0, resultArray.Length);
}
public static string Decrypt(string input, string key)
{
byte[] inputArray = Convert.FromBase64String(input);
TripleDESCryptoServiceProvider tripleDES = new TripleDESCryptoServiceProvider();
tripleDES.Key = UTF8Encoding.UTF8.GetBytes(key);
tripleDES.Mode = CipherMode.ECB;
tripleDES.Padding = PaddingMode.PKCS7;
ICryptoTransform cTransform = tripleDES.CreateDecryptor();
byte[] resultArray = cTransform.TransformFinalBlock(inputArray, 0, inputArray.Length);
tripleDES.Clear();
return UTF8Encoding.UTF8.GetString(resultArray);
}
}