I want to verify ECDSA signature generate on android by using python.
But I can't found object or any thing same as Signature object in Python.
Here is my verify code if using Java
String origin = txtOrigin.getText().toString();
try {
sig = Signature.getInstance("NONEwithECDSA","SC");
sig.initVerify(publicKey);
byte[] stringInput = origin.getBytes("UTF-8");
sig.update(stringInput);
txtVerify.setText(sig.verify(signatureBytes)+"");
} catch (Exception e) {
e.printStackTrace();
}
Related
For a payment API I need to hash a string (a request payload) with SHA-512,
sign itwith "RSA" according to the documentation.
Hash the payload string (payout instruction) using SHA512 algorithm.
Sign the hashed payload string using RSA algorithm and the signing certificate private key.
Base64 encode the signed hash
Step 1 and 3 I've got no problems with. Step 2 is the problem. Support sent me a java example but we don't run java and I would like to do this in OpenSSL if at all possible.
private static String createSignature(String stringToBeSigned, PrivateKey privateKey) {
try {
byte[] hashString = hashString(stringToBeSigned);
Signature sign = Signature.getInstance("SHA512withRSA");
sign.initSign(privateKey);
sign.update(hashString);
byte[] signature = sign.sign();
return Base64.getEncoder().encodeToString(signature);
} catch (Exception e) {
throw new RuntimeException("Could not create signed payout request.", e);
}
}
private static byte[] hashString(String stringToBeHashed) {
try {
MessageDigest digest = MessageDigest.getInstance("SHA-512");
return digest.digest(stringToBeHashed.getBytes(StandardCharsets.UTF_8));
} catch (Exception e) {
throw new RuntimeException(e);
}
}
The Key is provided. How do I find what "SHA512withRSA" corresponds to using OpenSSL?
I write code to sign string android using ECDSA algorithm.
Here is mycode:
String origin = txtChuoi.getText().toString();
try {
byte[] chuoiInput = origin.getBytes("UTF-8");
sig = Signature.getInstance("NONEwithECDSA","SC");
sig.initSign(privateKey);
sig.update(chuoiInput);
signatureBytes = sig.sign();
txtSign.setText(Base64.encodeToString(signatureBytes,Base64.DEFAULT));
} catch (Exception e) {
e.printStackTrace();
}
I can verify this sign string in same code app (using Java/Android). Here is my code:
String origin = txtChuoi.getText().toString();
try {
sig = Signature.getInstance("NONEwithECDSA","SC");
sig.initVerify(publicKey);
byte[] chuoiInput = origin.getBytes("UTF-8");
sig.update(chuoiInput);
txtVerify.setText(sig.verify(signatureBytes)+"");
} catch (Exception e) {
e.printStackTrace();
}
but not I want to verify it on my ubuntu server.
I have a trouble.
How can I implement verify code using python?
I cant write publickey code to pem file like this:
-----BEGIN PUBLIC KEY-----
MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEfUnusZsShxFLUuAwwAyFAkGCq3mBy98RXIkTP8YiTO3qmL8w6eMdMadiHfdCG2emktDrUwzNmTr9nMFCFhXdGQ==
-----END PUBLIC KEY-----
But how about the Signature? And I think (but not sure) it verify on bytes[].
How python do this?
Here's a similar question with the answer:
How to sign and verify signature with ecdsa in python
You'll need to prepare the public key for verification. The PEM file you mentioned has it base64 encoded.
I'm trying to interplate and implement the following statement.
Digitally sign the payload with Private Key using
RSASSA-PKCS1-V1_5 signature scheme and SHA1 cryptographic hash function.
Note: Refer to PKCS #1 v2.1: RSA Cryptography Standard specification for PKCS1-v1.5 Signature and Encryption scheme.
I'm confused when it says "and" sha1 hash function, below is adopted code which i'm not sure if it the right interpretation
public String getSignature(String _plainTextMessage,PrivateKey privateKey){
try {
Signature signer = Signature.getInstance("SHA1withRSA");
signer.initSign(privateKey);
signer.update(_plainTextMessage.getBytes());
byte[] signature = signer.sign();
return new BASE64Encoder().encode(signature);
} catch (NoSuchAlgorithmException e) {
e.printStackTrace();
} catch (InvalidKeyException e) {
e.printStackTrace();
} catch (SignatureException e) {
e.printStackTrace();
} catch (Exception e) {
e.printStackTrace();
}
return null;
}
or do i need to include MessageDiget like below
public String getSignature(String _plainTextMessage,PrivateKey privateKey){
try {
Signature signer = Signature.getInstance("SHA1withRSA");
signer.initSign(privateKey);
signer.update(_plainTextMessage.getBytes());
byte[] signature = signer.sign();
MessageDigest sha1 = MessageDigest.getInstance("SHA1");
byte[] digest = sha1.digest(signature);
return new BASE64Encoder().encode(digest);
} catch (NoSuchAlgorithmException e) {
e.printStackTrace();
} catch (InvalidKeyException e) {
e.printStackTrace();
} catch (SignatureException e) {
e.printStackTrace();
} catch (Exception e) {
e.printStackTrace();
}
return null;
}
I will appreciate any hint, and if applicable how do i verify the signature if i use the second option.
thanks
The first option makes sense and the second option makes very little sense; you'll need the first option: just using SHA1withRSA.
Calculating the hash is part of the signature generation operation. The signature generation operation allows you to configure the signing operation for a specific hash, e.g. SHA-1 or SHA-256. This is what you do when you specify SHA1withRSA. That it is using PKCS#1 v1.5 padding is implicit as at the time they wrote the function there was only one scheme that was widely standardized.
In your second piece of code you hash the signature. That's interesting, but it disallows you to verify the signature using the public key. And that's why you were generating the signature in the first place. Note that if you'd use a different undeterministic signature scheme such as PSS that you would get a different hash each time, rendering your second scheme completely useless.
Note that in general SHA-1 is not considered secure anymore and this is especially the case for signature generation. Only if the input to the signatue algorithm (and the underlying hash algorithm) is restricted could it still be considered secure.
I am going to integrate two web applications written in different platforms (Java and Ruby),
I have to use common encryption algorithm for password in both application.
Is there any common encryption/decryption algorithm for both? If yes, please mention any useful link or any example.
It would be highly appreciated. Thanks in advance
In addition during my digging out it I found,
I have used Base64 with DES in both, interesting thing is that Characters and special characters give me same result in both but as i adding any number like (1,2,3), half of result is same and half encryption is something different.
*Ruby Code
require 'openssl'
require 'base64'
c = OpenSSL::Cipher::Cipher.new("des")
c.encrypt
c.key ="REPPIFY_ABCDEFGHIJKLMNOPQRSTUVWXYZ"
e = c.update("ankit#123")
e << c.final
puts Base64.encode64(e)
Output: Cbe9GslMs8mh33jAOD9qsw==
*Java Code
I am defining only encryption method here:-
public static String encryptPassword(String pass) {
public static final String DESKEY = "REPPIFY_ABCDEFGHIJKLMNOPQRSTUVWXYZ";
System.out.println("Here is my password = "+pass);
DESKeySpec keySpec = null;
SecretKeyFactory keyFactory = null;
SecretKey key = null;
Cipher cipher = null;
BASE64Encoder base64encoder = new BASE64Encoder();
byte[] cleartext = null;
String encrypedPwd = null;
String pass = "ankit#123";
try {
keySpec = new DESKeySpec(DESKEY.getBytes("UTF8"));
keyFactory = SecretKeyFactory.getInstance("DES");
key = keyFactory.generateSecret(keySpec);
if(pass!=null) {
cleartext = pass.getBytes("UTF8");
cipher = Cipher.getInstance("DES");
cipher.init(Cipher.ENCRYPT_MODE, key);
encrypedPwd = base64encoder.encode(cipher.doFinal(cleartext));
}
} catch (InvalidKeyException e) {
e.printStackTrace();
} catch (NoSuchAlgorithmException e) {
e.printStackTrace();
} catch (InvalidKeySpecException e) {
e.printStackTrace();
} catch (UnsupportedEncodingException e) {
e.printStackTrace();
} catch (NoSuchPaddingException e) {
e.printStackTrace();
} // cipher is not thread safe
catch (IllegalBlockSizeException e) {
e.printStackTrace();
} catch (BadPaddingException e) {
e.printStackTrace();
}
System.out.println("Here I am printing encrypted pwd = "+encrypedPwd);
return encrypedPwd;
}
Output in Java :- Cbe9GslMs8mWn9yTmZrUiw==
Well, in the Ruby world, I'd recommend BCrypt, which is also favored by popular authentication plugins like Devise. I'm not very familiar with Java but a quick search suggests that there's BCrypt implementation in Java too:
http://www.mindrot.org/projects/jBCrypt/
EDIT - BCrypt is 1-way encryption, mainly for use in hashing passwords. If you are looking for something that will encrypt and decrypt then you'll have to look at something else. Seeing as you mentioned it's for passwords I'd suggest you only want 1-way encryption though.
I got the answer...just change a following line in ruby code and then you can use base64 decoder with DES in both:
c = OpenSSL::Cipher::Cipher.new("DES-ECB")
require 'openssl'
require 'base64'
c = OpenSSL::Cipher::Cipher.new("DES-ECB")
c.encrypt
c.key ="REPPIFY_ABCDEFGHIJKLMNOPQRSTUVWXYZ"
e = c.update("ankit#123")
e << c.final
puts Base64.encode64(e)
Am trying to authenticate a soap webservice, but the SHA1 hash that I produce in java is not working but the hash produced with .Net works.
What is the java equivalent for this .Net code?
//.Net
var token = "H?OIgSJ35~LKJ:9~~7&sUtHDeKAv*O#is?cEwV[}!i#u%}";
var shaProvider = new SHA1Managed();
var rawKey = Encoding.Unicode.GetBytes(token);
var rawHash = shaProvider.ComputeHash(rawKey);
var signature = BitConverter.ToString(rawHash).Replace("-", "").ToLower();
Hash produced:a508a29efeea2821e519fcbf64f164dd5d672233
//Java - This is what I tried using commons-codec-1.4.jar
String token = "H?OIgSJ35~LKJ:9~~7&sUtHDeKAv*O#is?cEwV[}!i#u%}";
MessageDigest cript = null;
try {
cript = MessageDigest.getInstance("SHA1");
} catch (NoSuchAlgorithmException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
cript.reset();
cript.update(token.getBytes());
String password = new String(Hex.encodeHex(cript.digest()));
System.out.println(password);
Hash produced:88e7c8fc13ac75e8efc8d0c00182caa6dc087093
My guess is that token.getBytes() doesn't use the same encoding as Encoding.Unicode.GetBytes(token), since you're unlikely to have UTF-16 Little Endian as your default charset. What happens if you change it to token.getBytes(StandardCharsets.UTF_16LE)?