In short, I have a integer value about 10 digits long. I would like to encrypt it using rc4 algorithm in Java. I went online and search, but I could only find encryption for string values/plaintext. Please advise. Thanks!
I assume that you are using the JavaSE API, in particular the javax.crypto.Cipher class. The encryption API is concerned with generic data, not interpreted in some way; this is why Cipher#doFinal() takes a byte array. (You may interpret that as a string, given the common terms "plaintext"/"ciphertext".)
The solution to your problem is to convert the integer to a byte array. If "integer" in your case means int (32-bit), then you need 4 bytes (8-bit). See this question for (multiple good) solutions to this.
Can't you just convert the integer to a String and then encrypt the string?
String myIntegerString = Integer.toString(myInteger);
encrypt myIntegerString;
store the encrypted myIntegerString;
read the encrypted myIntegerString;
decrypt myIntegerString;
Integer.parseInt(myIntegerString).
Related
I'd like to validate that a String is a sha256 representation of another without having to decrypt it. Is this possible?
Yes and no.
You can test that a string is hex very easily. You can then test that it contains a statistically sensible number of digits and letters. That will rule out some common non sha256 strings.
But if someone creates a random string designed to look like a sha256, I don't think it's possible to distinguish it from the real thing by any mathematical test. The algorithm is designed to be robust to that.
A sha-256 value is just a 256 bits (32 bytes) value which you usually represent as a String or as a byte[] in Java.
As a value per se it's pointless, if you want to tell if a specific String is a hash then any 32 bytes number is a hash of an infinite unknown plain texts. But it's like asking "how do I know that a 32 bytes number is a number?", you see that you are going nowhere.
It's useful only when it's paired to a plain text so that you can compare it with the hash computed from the plain text to verify they match.
I think what you could do is to hash the other string and then compare these two strings with each other.
No idea if this would help you but I read that it was commonly used praxis when creating rainbow tables for cracking password attempts.
EDIT: Oh forgot this is also the way to compare passwords in php when you login to a webpage iirc. At least I had to do it like this for university.
This question already has answers here:
How to decrypt a SHA-256 encrypted string?
(4 answers)
Is it possible to decrypt MD5 hashes?
(24 answers)
Closed 8 years ago.
Please let me know equivalent code to decrypt. I have encrypted my password using this encode method and now i want to decrypt now.
MessageDigest digest = MessageDigest.getInstance("MD5");
digest.update(password.getBytes());
BASE64Encoder encoder = new BASE64Encoder();
byte hashedBytes[] = (new String(digest.digest(), "UTF-8")).getBytes();
System.out.println(encoder.encode(hashedBytes))
Short answer is you can't. MD5 is a hash, which means that data "encrypted" with it theoretically cannot be turned back into the original data. It's a one-way function, that (theoretically) cannot be reversed. Read up on cryptographic hash functions to find out more.
It's like if you had a machine that processed books by returning the number of pages in the book. You can feed it a book, and you'll get a value back, but given only the output from the machine it's impossible to tell what was fed in.
More details:
From the Wikipedia page for a cryptographic hash function:
A cryptographic hash function is a hash function that takes an arbitrary block of data and returns a fixed-size bit string, the cryptographic hash value, such that any (accidental or intentional) change to the data will (with very high probability) change the hash value.
The ideal cryptographic hash function has four main properties:
it is easy to compute the hash value for any given message
it is infeasible to generate a message that has a given hash
it is infeasible to modify a message without changing the hash
it is infeasible to find two different messages with the same hash.
Note bullet point 2. This means that it'll be effectively impossible to produce your password from the hash.
Granted, MD5 is considered cryptographically unsafe, but it still means that there isn't a general way to go from hash to input.
I am trying to send an encrypted text with each HttpResponse and when I get the next HttpRequest with the encrypted text, I decrypt it and do some stuff :) with it.
I am curious about the best practices surrounding the storage/retrievel of the keys and ivSpec's (or nonce's) in general, but specifically looking at the code posted by #sherif based on #VoidPointer 's suggestions in How to encrypt String in Java,
a) Do we have to initialize ivSpec with random bytes for each string that I want to encrypt?
b) If so, do we store the generated ivSpec in some db and look it up when I need to decrypt using that?
c) If so, how do we look it up? When an encrypted string needs to be decrypted how do we pick the correct ivSpec from db?
d) One suggestion is to send ivParameter along with the encrypted string! itself (which is probably what is happening with #sherif 's implementation!). If we chose to do so, how can I modify the class provided by #sherif to decrypt and separate the iv parameter and encrypted string instead of providing the iv parameter while initializing decrypt cipher?
A. If you do not change the vector, each time you encrypt the same string, you get the same encrypted result.
By changing the IV each time, you make it so that every single encrypted output looks different (even if it's the same input).
Think of it as a the "salt" you use when you are hashing a password.
so under normal circumstances it would be desirable to use a random iv.
B&C. You need to look the IV up, yes. But storing it into a DB isn't very useful. You already have a piece of information that you keep stored secretly: that's the password. IV is just here to increase randomness, no need to keep it, push it out with the output.
D. Sending it is the usual way to go.
One way is to concatenate it at the beginning of the ouput. (output = IV + encrypted data). Then before decrypting first split the input (IV = 32 first bytes of input) and decrypt the rest (crypt_data_to_decrpt = input after byte number 32)
Another way is to have a constant IV and a random part at the beginning:
you simply use a string of NUL byte as an IV.
Then you encrypt 32 bytes of pure random garbage
Then you encrypt your input. (When using a good encryption method, this should always produce a different encrypted output because the beginning was different).
For decryption, you use the same empty IV, then you decrypt everything. You ignore the 32bytes at the beginning. You split and only take the bytes after the 32nd. That's your decrypted output.
I'm encrypting a string say "hello h r u"
Using encryption algorithm and getting the encrypted String as b�*-ت5Tr���6=
This String we cannot send as an sms
So i want to convert to sms supported format by converting it into 7 bit.
and on the receiver side we have to convert back into 8 bit and decrypt.
How can i achieve this?
Note: I have used Base64 to convert into sms supported format but the length is increasing.
So iam not able to send more character
I'm assuming your question is something like:
How can I transmit my binary data as valid SMS text without increasing the size of the message?
The answer for this is - you can't - at least not with 100% certainty.
Your encryption algorithm probably creates some byte array (byte[]) which will grow by around 33% (as stated in the above comments) once you Base64 encode it.
The only option I see is to attempt to compress the information either before or after encryption - depending on which compression algorithm you choose - and then Base64 encode it. This will give you a better chance of making the size limit - but nothing definitive. (Unless you find a compression algorithm which promises to compress by more than 33% for every input.
An alternative is to span the message over two SMS messages - assuming you are allowed to do that.
I'm playing with the El Gamal cryptosystem, and my goal is to be able to encipher and decipher long sequences of text.
El Gamal requires the plaintext to be an integer. I have turned my string into a byte[] using the .getBytes() method for Strings, and then created a BigInteger out of the byte[]. After encryption/decryption, I turn the BigInteger into a byte[] using the .toByteArray() method for BigIntegers, and then create a new String object from the byte[].
I am using a 1035 bit key, and this works perfectly when I encipher/decipher with strings up to 129 characters. With 130 or more characters, the output produced from my decipher method is garbled.
Can someone suggest how to solve this issue?
Just like in RSA, you cannot encrypt a value larger than the modulus in ElGamal.
You can try
BigInteger pText = new BigInteger(plaintext.getBytes("UTF-8"));
to make the encoding/decoding and enciphering/deciphering more symmetric, but I'm not sure if that's the root cause.
By the way, you should never silently consume an Exception. The very least you can do is just catch (UnsupportedEncodingException e).
You need to use positive numbers for your operations. So you must construct BigInteger like this,
BigInteger pText = new BigInteger(1, plaintext.getBytes());
// 1: select a random integer k such that 1 <= k <= p-2
BigInteger k = abs(new BigInteger(p.bitLength() - 2, sr));
If you want to encrypt certain data with asymmetric cryptographic algorithm, you can do this only for really short data block. The reasons are both "technical" (the algorithm works this way) and "practical" (asymmetric cryptography is slow).
The right way to encrypt the large block of data using asymmetric cryptographic algorithm is
generate random ("session") key for some symmetric algorithm (AES, RC4, 3DES, you name it).
use this algorithm to encrypt the data
use your asymmetric algorithm to encrypt the session key
store the encrypted key near the data.
stop reinventing the wheel