Create RSA publickey/privatekey
Hello, everyone,
Instead of using KeyPairGenerator or keytool to generate RSA keys, I wrote a program to generate the RSA elements: p, q, n, public exponent e and private exponent d, the type of them are all BigInteger.
But here comes the question:
How can I convert these two element--e and n--into a PublicKey type? and also, how to convert d and n into PrivateKey type?
(The reason why I didn't use KeyPairGenerator or keytool is because I have some special requirement for p and q--the length of p and q are significant different in my project--other way can not reach this goal)
Thank you in advance for any help!
Regards
The *Key classes are interfaces. If you have all the info necessary, just make sure your objects implement RSAPrivate/PublicKey, and you should be set.
Grant
Similar Messages
-
Reading a PublicKey \ PrivateKey type from a txt file
Hi,
i want to read a PublicKey \ PrivateKey type from a txt file and input it into a method.
How can i read the data from the file while keeping or converting back to PublicKey \ PrivateKey type?
I'm working with the following:
generate = KeyPairGenerator.getInstance("ECDSA", "FlexiEC");
generate.initialize(ecParams, new SecureRandom());
KeyPair keyPair = generate.generateKeyPair();
............continues
**and then i write the keys to the a simple txt file.**
thanks!
Edited by: sk16 on Apr 8, 2010 10:03 PMSo, if i work with the two above is it ok, like:
generate = KeyPairGenerator.getInstance("ECDSA", "FlexiEC");
generate.initialize(ecParams, new SecureRandom());
KeyPair keyPair = generate.generateKeyPair();
// Pub. and Priv. key objects.
PublicKey publicKey = keyPair.getPublic();
PrivateKey privateKey = keyPair.getPrivate();
// Write keys to separate files.
FileOutputStream fos = new FileOutputStream(publicKeyFile);
fos.write(publicKey.getEncoded());
fos.close();
FileOutputStream fos1 = new FileOutputStream(privateKeyFile);
fos1.write(privateKey.getEncoded());
fos1.close();
and then for example>>>
DataInputStream in = new DataInputStream(
new FileInputStream("publicKeyFile.txt"));
byte[] encodedPublicKey = new byte[1024];
in.read(encodedPublicKey);
in.close();
X509EncodedKeySpec encodedPublicKeySpec = new X509EncodedKeySpec(encodedPublicKey);
KeyFactory keyFactory = KeyFactory.getInstance("ECDSA", "FlexiEC");
publicKey = keyFactory.generatePublic(encodedPublicKeySpec); -
Convert strings to publicKey/privateKey objects
Hi,
I have the following problem : I'm generating RSA key pairs in string formats. I want to sign an XML document so I have to specifiy KeyPair object in order to do that.
How can I convert string to publicKey and privateKey objects ?
i.e How can I correct this code :
String pubKey = generatePublicKey();
String priKey = generatePrivateKey();
KeyPair kp = new KeyPair(pubKey,priKey);
// sign the XML documents
Thanks a lot for your precious help.
Cheers,
Othman.http://forum.java.sun.com/thread.jspa?threadID=577716&tstart=0
-
Create RSA keys based on p and q
Is there a way to create a KeyPair based on p and q (BigIntegers or byte[])
The reason i need this is because i need to encrypt files that need to be decrypted in a c# program (and vice versa). The encryption needs to be RSA (so no DES or....) although i know that there is not really a need for asymetric encryption.
The problem is I can generate a keypair in Java but then i cannot get the data for that keypair in c# (and vice versa).
In c# i can create an equivalent of a keyPair based on p and q or on so if there would be a way to get the p and the q of a generated keypair that would also help (or all the other paramets, d, n, e, phi,....).
ThanksYou can generate a PKCS8 private key bytes and X509 public key byte using something like
final KeyPairGenerator rsaKeyPairGenerator = KeyPairGenerator.getInstance("RSA");
rsaKeyPairGenerator.initialize(2048); // or whatever size you want
final KeyPair rseKeyPair = rsaKeyPairGenerator.generateKeyPair();
// The private key as PKCS8 bytes
final byte[] privateKeyAsBytes = rseKeyPair.getPrivate().getEncoded();
// The public key as X509 bytes
final byte[] publicKeyAsBytes = rseKeyPair.getPublic().getEncoded();then you can import the X509 into C# (C# must have a way of importing an X509).
OR
do a similar thing in C# and export the X509 public key and import it into Java.
The private key should only be used by either the C# or Java application (not both) and I would expect whichever needs the private key should generate the key pair. -
CSS + SSL - unable to create RSA association
Hello,
I am having troubles creating an RSA association on our CSS11506.
Here are the steps I've tried:
1.) I take the original "Digital ID Class 3 - VeriSign Server OnSite" certificate provided to us and move to the CSS via FTP. I have used the openssl verify process to make sure it was a good cert.
CSS-EC1# copy ssl ftp FTPSRV import websrv-gr.pem PEM "thepassword"
Connecting (/)
Completed successfully.
(also at this step - I have tried this with and without a passphrase with the same results)
OpenSSL verify:
C:\OpenSSL\bin>openssl verify -verbose -CAfile .\PEM\verisign.pem websrv-gr.pem
websrv-gr.pem: OK
2.) I then create a certificate association:
CSS-EC1(config)# ssl associate cert WWW websrv-gr.pem
3.) I then attempt to create and RSA association:
CSS-EC1(config)# ssl associate rsakey WWW-RSA websrv-gr.pem
%% File does not contain an RSA key
What can I do to get rid of this error? Does the certificate we recieved from Verisign need to be chained with the Verisign Intermediate certificate?
Any ideas?
Thanks in advance...
Regards,
BenHi
we have a customer with a similar problem,
CSS11501(config)# ssl associate rsakey vimageprivkey privkeyvimages.pem
Error: %% File does not contain an RSA key
The openssl utility has been used to extract the rsakey from the PKCS12 file.
They have used this method numerous times before without this error.
RSA key below:-
Bag Attributes
localKeyID: 31 31 36 33 30 38 34 35 35 32 32 33 30
friendlyName: vimages 2006 certificate
Key Attributes:
-----BEGIN RSA PRIVATE KEY-----
Proc-Type: 4,ENCRYPTED
DEK-Info: DES-EDE3-CBC,4B31C6E8188C1E2C
L2zTgx4mEUBG0465IxpNOfeyoMX8vTXF6TTrClc5BCDqEYa+K8/9yu6ZwQ+GKdV2
WN0NES4mNMyqB+j2K9ysQi59Zw661MSf/ToTLPgbFlI7xK434ZpMiy6K0VIK8cSW
Nz8yTSbjarpsrigUYzoJ83p10a6vVXA/dEDGrMn84EQeYWjQdStcHU8DKmgaOMLY
c3s68BHex2oNOdG4P4Uo4lTG1zmQOyP0aY7KHv0KNVrR/RNSW4j01nAdPZ09YiiZ
Uu83Kvh/kwkGBhGYAr0vnlqPlsdUarfXams39F/Imp3NQdofXsrVencUjST4zjPK
1xpptY2RYa4lCEZBF5+Y00QhxaQR8IuLkh0x2niR/Nz+KBHxOJ8hacB/bcIpZKv0
ikFDiXoGLgRNCRM1qhECyfUk4Gt95J4qKSAsyUNOTjhaz73q+sUPu6eLffwUQ1U2
g6fNcqAu6z5xJkpPjVtGVt+opERqGrnlCW2R6I1QYio+U21p4Cx+7qfxrGGpZtt+
p0kYhEH9ZMODh8QhDEDv7qqLASQ5aQMcJSLIXCrV13R+yN/qr8qOUDKA88a9avIg
cArcSEWSQ91ZxYYIijnqMHNBWs1REM6U/FRuW28yM4JtZTyxB8baZUVczAfOnOja
yAuJ0UVyshNOZxk5W1OJTjrkqY7+JM0CdnJuYUSqvsQb9L3hiAJ/wHzUQw5pN1J3
Igoo6eLoBj2QC2Fgz1TwJEohelF3F+BVlEvjWjPHi5D0r2e1+HDNNjpWWZctebp7
Aw7kguV1bymfiG3stoHkP/VU2MyCznS6vXI/PWh4KgI=
-----END RSA PRIVATE KEY-----
Any Ideas ?? -
Is there anyway by whicch I can test my RSA signed applet by using self issued certificates??
I created a RSA signed applet using the documentation available on
http://java.sun.com/products/plugin/1.3/docs/rsa_signing.html
I used a self-signed certificate but it doesn't work. It gives me a security exception.Found a way :)
Details at http://forum.java.sun.com/thread.jsp?forum=63&thread=152882
Cheers
Abraham Khalil -
I can�t decrypt a text encrypted (using RSA) with keys on smartcard.
I use a Cyberflex Access e-gate smartcard and I can encrypt and decrypt any text on the card but if I encrypt a text outside using the exported public key, card is not able to decrypt the message.
On the card side:
�
RSAPrivateCrtKey privateKey;
RSAPublicKey publicKey;
Cipher cipherRSA;
�
private MyIdentity (byte buffer[], short offset, byte length){
// initialise PIN
pin = new OwnerPIN(PinTryLimit, MaxPinSize);
pin.resetAndUnblock();
// Key Pair
KeyPair kp = new KeyPair(KeyPair.ALG_RSA_CRT, (short)1024);
kp.genKeyPair();
privateKey = (RSAPrivateCrtKey) kp.getPrivate();
publicKey = (RSAPublicKey) kp.getPublic();
cipherRSA = Cipher.getInstance(Cipher.ALG_RSA_PKCS1, false);
if (buffer[offset] == (byte)0) {
register();
} else {
register(buffer, (short)(offset+1) ,(byte)(buffer[offset]));
private void GetPublicKey (APDU apdu) {
if (pin.isValidated()){
byte apduBuffer[] = apdu.getBuffer();
// short byteRead = (short)(apdu.setIncomingAndReceive());
short bytesMod = publicKey.getModulus(apduBuffer, (short) 0);
short bytesExp = publicKey.getExponent(apduBuffer,bytesMod);
short outbytes = (short) (bytesMod + bytesExp);
// Send results
apdu.setOutgoing();
// indicate the number of bytes in the data field
apdu.setOutgoingLength((short)outbytes);
// at offset 0 send 128 byte of data in the buffer
apdu.sendBytesLong(apduBuffer, (short)APDUDATA, (short)outbytes);
} else {
ISOException.throwIt (ISO7816.SW_SECURITY_STATUS_NOT_SATISFIED);
private void Decrypt (APDU apdu) {
byte apduBuffer[] = apdu.getBuffer();
short byteRead = (short)(apdu.setIncomingAndReceive());
cipherRSA.init(privateKey, Cipher.MODE_DECRYPT);
cipherRSA.doFinal(apduBuffer,(short)APDUDATA, byteRead, apduBuffer, (short)APDUDATA);
// Send results
apdu.setOutgoing();
// indicate the number of bytes in the data field
apdu.setOutgoingLength(byteRead);
// at offset 0 send x byte of data in the buffer
apdu.sendBytesLong(apduBuffer, (short)APDUDATA, byteRead);
}Off the card, I have a java client:
public void getPublicKey () {
int CLA, INS, P1, P2;
int iArray[] = new int[0];
short sArray[] = new short[0];
String ss = new String("");
String s;
byte [] sBytes = null;
byte [] myModulus = new byte[128];
byte [] myExponent = new byte[3];
try {
CLA = 0x68;
INS = 0x78;
P1 = 0;
P2 = 0;
sArray = iopCard.SendCardAPDU(CLA,INS,P1,P2,iArray,0x83);
int iErrorCode = iopCard.GetLastErrorCode();
if (iErrorCode != 0x9000) {
if (iErrorCode == 0x6300) {
System.out.println("Wrong PIN");
} else {
s = iopCard.GetErrorMessage();
System.out.println("SendCardAPDU: " + s);
} else {
System.out.println("Getting Public Key...");
if (sArray != null) {
sBytes = new byte[sArray.length];
for (int i = 0; i < sArray.length; i++) {
sBytes[i] = (byte)sArray;
ss = new String(sBytes);
System.out.println ("------ BEGIN PUBLIC KEY -------------------");
for (int i=0; i < sArray.length; i++){
System.out.print(Integer.toHexString(ss.charAt(i)).toUpperCase());
System.out.println ();
System.out.println ("------ END PUBLIC KEY -------------------");
} else {
System.out.println("Nothing.");
} catch (slbException b) {
s = b.getMessage();
System.out.println("Validate error: " + s);
for (int i=0; i<128; i++){
myModulus[i] = (byte) sArray[i];
for (int i=0; i<3; i++){
myExponent[i] = (byte) sArray[128+i];
BigInteger modulus = new BigInteger (1,myModulus);
BigInteger exponent = new BigInteger ("65537"); // there is a well-known bug in getExponent
RSAPublicKeySpec keySpec = new RSAPublicKeySpec(modulus, exponent);
KeyFactory keyFactory =null;
try {
keyFactory = KeyFactory.getInstance("RSA");
publicKey = keyFactory.generatePublic(keySpec);
} catch (NoSuchAlgorithmException e) {
System.out.println(e.getMessage ());
} catch (InvalidKeySpecException e) {
System.out.println(e.getMessage ());
System.out.println("------------------ BEGIN ------------------");
ss = new String(publicKey.getEncoded());
for (int i=0; i < publicKey.getEncoded().length; i++){
System.out.print(Integer.toHexString(ss.charAt(i)).toUpperCase());
System.out.println ();
System.out.println("------------------ END ------------------");
// to a file
try {
//Store in raw format
FileWriter fw = new FileWriter("public_raw.txt");
for (int i=0; i < publicKey.getEncoded().length; i++){
fw.write(Integer.toHexString(ss.charAt(i)).toUpperCase());
fw.close();
//could also store it as a Public key
System.out.println("Public key saved to file");
} catch(Exception e) {
System.out.println("Error opening and writing Public key to file : "+e.getMessage());
public void encrypt () {
byte cadena[] = {0x01,0x02,0x03,0x04};
byte resultado[] = new byte[256];
// Create Cipher
try {
cipherRSA.init(Cipher.ENCRYPT_MODE, publicKey);
resultado = cipherRSA.doFinal (cadena);
} catch (InvalidKeyException e) {
System.out.println(e.getMessage());
} catch (BadPaddingException e) {
System.out.println(e.getMessage());
} catch (IllegalBlockSizeException e) {
System.out.println(e.getMessage());
String ss = new String (resultado);
System.out.println("------------------ BEGIN 4 ------------------");
for (int i=0; i < resultado.length; i++){
System.out.print(Integer.toHexString(ss.charAt(i)).toUpperCase());
System.out.println ();
System.out.println("------------------ END 4 ------------------");
Another question is that I don�t understand why I get a constant length string when I encrypt a text on the card and variable length string when I encrypt off the cardI thought that exponent was 3 bytes long...
On the card I have the following code:
private void GetExponent (APDU apdu) {
if (pin.isValidated()){
byte apduBuffer[] = apdu.getBuffer();
short bytesExp = publicKey.getExponent(apduBuffer, (short) 0);
// Send results
apdu.setOutgoing();
// indicate the number of bytes in the data field
apdu.setOutgoingLength((short)bytesExp);
// at offset 0 send 128 byte of data in the buffer
apdu.sendBytesLong(apduBuffer, (short)APDUDATA, (short)bytesExp);
} else {
ISOException.throwIt (ISO7816.SW_SECURITY_STATUS_NOT_SATISFIED);
}And if I don't send an APDU with length expected, I get the exception 6C03 (Correct Expected Length (Le) = 0x6C00) so I send APDU with 03 length and I receive the exponent. The problem is that there is a well know bug in getExponent and it returns 00 00 00... so I set it up to 65537 outside the card. -
How to remove padding after RSA decryption??
Hello,
I am testing my host apps ability to read public key that was saved in file after being exported from smart card where it was generated.
I have successfully used the private key on card to encrypt a small piece of data and the cryptogram is returned to the host.
On host side I retrieve public key from file and decrypt ciphertext
The on-card alg for Cipher is declared as follows-
RSAcipher = Cipher.getInstance(Cipher.ALG_RSA_PKCS1, true);and in the host app
Cipher rsaCipher = Cipher.getInstance("RSA","BC");I can see from what is returned from
byte[] decrypted = rsaCipher.doFinal(this.encryptedData);that the correct data is being returned, but is is padded by
01FFFFFFFFFFFFFFFFFFFFFFFFFFFFFF
FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF
FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF
FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF
FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF
FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF
FFFFFFFFFFFFFFFFFFFFFFFFFFFF00How do I know where the padding ends and the plaintext begins?
Can anyone help me with this?
Thanks in advance,
AnnHi!
I have the same problem like you.
But my problem is that i don,t know how to move the key across. I manege to create a pair of keys public and private using RSA Algorithm.
privateKey = KeyBuilder.buildKey(KeyBuilder.TYPE_RSA_PRIVATE,KeyBuilder.LENGTH_RSA_512,false);
publicKey = KeyBuilder.buildKey(KeyBuilder.TYPE_RSA_PUBLIC,KeyBuilder.LENGTH_RSA_512,true);
// KeyPair creation
if(keyPair == null){
keyPair = new KeyPair(KeyPair.ALG_RSA, (short)publicKey.getSize());
// starts key generation process
keyPair.genKeyPair();
publicKey = keyPair.getPublic();
privateKey = keyPair.getPrivate();
cipher = Cipher.getInstance(ALG_RSA_NO_PAD, false );then i send the modulus and exponent part of the public key to host
byte keyElement = (byte)(apduBuffer[ISO7816.OFFSET_P2] & 0xFF);
// check correct type (modulus or exponent)
if((keyElement != 0x00) && (keyElement != 0x01))
ISOException.throwIt(ISO7816.SW_INCORRECT_P1P2);
// check elements request
if(keyElement == 0) {
// retrieve modulus
apduBuffer[0] = (byte)((RSAPublicKey)publicKey).getModulus(apduBuffer, (short)1);
} else
// retrieve exponent
apduBuffer[0] = (byte)((RSAPublicKey)publicKey).getExponent(apduBuffer, (short)1);
// send the key element
apdu.setOutgoingAndSend((short)0, (short)((apduBuffer[0] & 0xFF) + 1));I decrypt the data as follow in the card
byte[] apduBuffer = apdu.getBuffer();
if(!privateKey.isInitialized())
ISOException.throwIt(ISO7816.SW_CONDITIONS_NOT_SATISFIED);
cipher.init(privateKey,Cipher.MODE_DECRYPT);
apdu.setIncomingAndReceive();
cipher.doFinal(apduBuffer, (short)ISO7816.OFFSET_CDATA, (short)(apduBuffer[ISO7816.OFFSET_LC] & 0xFF), apduBuffer, (short)0);
apdu.setOutgoingAndSend((short)0, (short)(KeyBuilder.LENGTH_RSA_512/8));
in host i encrypt data as follow
// Note modulus and exponent are arrays of bytes from the card
BigInteger modulus = new BigInteger(1,modulus);
BigInteger exponent =new BigInteger(1,exponent);
cipher = Cipher.getInstance("RSA");
RSAPublicKeySpec pubKeySpec = new RSAPublicKeySpec(modulus,exponent);
keyFactory = KeyFactory.getInstance("RSA");
pubKey = keyFactory.generatePublic(pubKeySpec);
cipher.init(Cipher.ENCRYPT_MODE,pubKey);
byte[] p = cipher.doFinal(data); -
Hi,
Since the 1 of January, 2011 all portuguese invoices must be signed up digitally and registered.
We have come up to the following solution:
With the help of OPENSSL generate a private key:
OPENSSL GENRSA -OUT privatekey.PEM 1024
It must fulfill the following requisites of RSA algorithm:
-> Format = x.509
-> Charset = UTF-8
-> Encoding = Base-64
-> Endianess = Little Endian
-> OAEP Padding = PKCS1 v1.5 padding
-> Length private key = 1024 bytes
-> Mensage Format Hash = SHA-1
Then on the basis of the private key a public key should be generated:
OPENSSL RSA -IN privatekey.PEM - OUT publickey.PEM -OUTFORM PEM -PUBOUT
With the help pf the HOST command I create the signatures for the invoice registry:
cmd> echo TEXT.TXT | openssl dgst -sha1 -sign privatekey.pem | openssl enc -base64
where the file TEXT.TXT is: "2010-05-18;2010-05-18T11:22:19;FAC 001/14;3.12;"
It has been an horrible, but efficient solution.
It functions well when you register an invoice, but it gets complicated when you want to verify if the signatures are correct.
Reasons:
- You have to filter all the documents and all the registries must execute the Host command in the background.
The command will open and create files for each verification.
When you delete these files it continues in the registry...
What I´m asking is whether there is a better, more efficient way to generate signatures in pl/sql as well as their verification?
Regards
JomarHi Jomar,
correct me if I'm wrong, but from your post it looks like what you are doing is capturing the ouput from an OS command to manipulate within the database. If you search this forum or google for something like "execute OS command from PL/SQL" you will get lots of hits. Also, have you searched to see if there is a java based equivalent to openssl which could be compiled in and called from the Oracle database.
Andre -
Reading PublicKey from a text file..
Hi,
I generated Public Key using RSA algorithm, and getEncoded() using Base64Encoder, after that I saved it as TEXT file. Here goes the code.
KeyPairGenerator keyGen = KeyPairGenerator.getInstance("RSA");
keyGen.initialize(512);
KeyPair keypair = keyGen.generateKeyPair();
PublicKey publicKey = keypair.getPublic();
PrivateKey privateKey = keypair.getPrivate();
//Get bytes of the public and private keys
byte[] privateKeyBytes = privateKey.getEncoded();
byte[] publicKeyBytes = publicKey.getEncoded();
byte[] keypb = publicKey.getEncoded();
BASE64Encoder pubEncod = new BASE64Encoder();
String pub64 = pubEncod.encode(publicKey.getEncoded());
char c1[] = new char[pub64.length()];
pub64.getChars(0, pub64.length(), c1, 0);
String fileName1 = "D:\\PublicKey\\PublicKey.txt";
FileWriter f1 = new FileWriter(fileName1);
f1.write(c1);
f1.close();
After that, I tried to decoded PublicKey from this text file, using this code..
//Read public Key from txt file
//FileReader
FileReader fr = new FileReader("D:\\PublicKey\\PublicKey.txt ");
//BufferedReader - uses the FileReader
BufferedReader br = new BufferedReader(fr);
//String to contain lines from the file
String s;
//StringBuffer used store the file contents
StringBuffer sb = new StringBuffer("");
//Final output from the operation
String output;
//Loop through lines of the file, storing the file content
while((s = br.readLine()) != null)
{ sb.append(s + "<br>");
//Store the file contents in the output string
output = sb.toString();
//Close the file
fr.close();
BASE64Decoder decoder = new BASE64Decoder();
byte[] decodedPublicKey = decoder.decodeBuffer(output);
// bytes can be converted back to public key
X509EncodedKeySpec pubKeySpec = new X509EncodedKeySpec(decodedPublicKey);
KeyFactory keyFactory = KeyFactory.getInstance("RSA");
PublicKey pubk = keyFactory.generatePublic(pubKeySpec);
And got InvalidKeyException and lengthTag is TOO BIG.. Any one can tell what is the problem while reading back??
Thanks
Ameriwhile((s = br.readLine()) != null)
{ sb.append(s + "<br>");
//Store the file contents in the output string
output = sb.toString();Hi,
Ouch! Your extra data is probably coming from the <br>s. the 'b' and 'r' are being Base-64 decoded and producing extraneous bytes. I'm not sure why you have the <br> in there, but try removing it an see what happens. Good luck. -
Create FXDContent from raw FXD string
Hi,
Just wondering if anyone might know whether it's possible to directly instantiate an FXDContent object using a string which contains FXD?
For example, the string would be "*FXD { content: [Ellipse { centerX: 100.0 ... }*".
It seems that the only way to create either an FXDContent object or FXDNode is via a load of a (well-formed) URI using FXDLoader.
(Hopefully in my noob-ness i haven't missed something here!)
I would like to be able to use my own subclass of HttpRequest to request FXD, in addition to other business data, from my servlet and manage the response (incl. headers, etc.) and load the FXD manually into an FXDContent object.
This would neatly avoid hitting the servlet once for the business data, and then hitting it again via the FXDLoader.
Just wondering if this would be possible, or if there are workarounds?
[I am using NetBeans 6.9.1 and JavaFX 1.3.1, and i have searched but not found any particularly relevant threads on the forum.]
Thanks in advance,
SteveI found a way using the BC provider (1.3.6). It goes like this.
import org.bouncycastle.asn1.pkcs.PKCSObjectIdentifiers;
import org.bouncycastle.asn1.x509.AlgorithmIdentifier;
import org.bouncycastle.asn1.x509.SubjectPublicKeyInfo;
AlgorithmIdentifier algid =
new AlgorithmIdentifier(PKCSObjectIdentifiers.sha1WithRSAEncryption);
SubjectPublicKeyInfo spki = new SubjectPublicKeyInfo(algid, rawKeyBytes);
byte[] x509KeyBytes = spki.getDEREncoded();The x509KeyBytes may now be used to create a PublicKey using the security API.
KeyFactory keyFactory = KeyFactory.getInstance("RSA");
Key publicKey = keyFactory.generatePublic(new X509EncodedKeySpec(x509KeyBytes));I would really like to avoid using the BC API directly, and rather use the standard API all the way. So any ideas are certainly welcome!
I noticed a slight difference in the length of the algorithm identifier created this way compared to using the IAIK provider as shown in may original posting, 20 vs 22 bytes respectively. Below the algid + first bytes of the raw key bytes are show hex-encoded.
BC: 30819d300b06092a864886f70d01010503818d00 30818902818100..
IAIK: 30819f300d06092a864886f70d010101050003818d00 30818902818100..As I haven't found a good definition of these bytes I don't what the difference is, but since both keys appear to work equally well I guess I should be happy with that.
Dagbj�rn -
Creating Token for Login Method
I am writing a login method that will authencticate user and return token for web services. Next time user will send is token and we will validate the token but requirement is that we donot wnat to keep any state of token at server.What does it mean that when we receive token, we should be able to detremine is it a valid token or not.(This implied token can't be forged by any user).
I have written a function using KeyPairGenerator, please have a look and let me know if you see any security issue.
Design is
token generateToken(userid) {
hash = hash(userid) ------------------- ONE
Signature = Encrypt (Private key , hash) --------------- TWO
return hash + " " + Signature
bool isValid(token) {
separate part 1 and part 2 of toekn (delimeter is space)
Signature = Encrypt (Public key , part1)
if signature == part2
token is valid
else token is invalid
Code is
PublicKey privateKey ;
PrivateKey publicKey ;
KeyPairGenerator keyGen;
SecureRandom random ;
KeyPair keypair;
public String generateToken() throws Exception{
keyGen = KeyPairGenerator.getInstance("DSA");
random = SecureRandom.getInstance("SHA1PRNG", "SUN");
keyGen.initialize(512 , random);
keypair = keyGen.genKeyPair();
privateKey = keypair.getPrivate();
publicKey = keypair.getPublic();
String token = userName;
byte[] part1 = getHash(1000, token , generateSalt());
/* Create a Signature object and initialize it with the private key */
Signature dsa = Signature.getInstance("SHA1withDSA", "SUN");
dsa.initSign(privateKey);
/* Update and sign the data */
dsa.update(part1, 0 , part1.length) ;
/* Generate a signature for it */
byte[] realSig = dsa.sign();
String tokenToReturn = byteToBase64(part1) + " " + byteToBase64(realSig) ;
return tokenToReturn;
public void verifyToken(String token) throws Exception{
int space = token.indexOf(" ");
String part1 = token.substring(0 , space);
String part2 = token.substring(space+1);
/* create a Signature object and initialize it with the public key */
Signature sig = Signature.getInstance("SHA1withDSA", "SUN");
sig.initVerify(publicKey);
byte[] bPart1 = base64ToByte(part1);
byte[] bPart2 = base64ToByte(part2);
/* Update and sign the data */
sig.update(bPart1, 0 , bPart1.length) ;
if ( sig.verify(bPart2) )
System.out.println("signature verifies: " );
else
System.out.println("signature does not verifies: " );
Does this code look right ??? Please let me know if you see any pitfalls or know better way to create tokenHello,
one conceptual problem is the fact that once you generate such a token it is valid forever. One idea would be to incorporate the date/time of generation, so that you have some kind of timeout mechanism if the token is too old. Again, the token mechanism will be susceptible to replay attacks for the token's validity period.
For my part, I would tend to go with some kind of one-time token design. Even if you are constrained not to use a database, you could use an in-memory structure to keep track of the generated tokens, mapping them to the users requested them and removing them on an explicit logout or after an expiration time period. This way you don't depend on a timestamp, which implies that you keep a clock well-synchronized. Just my $.02.
Kind regards,
Anestis -
Help with RSA Encryption using SATSA
Hello,
I am a new to writing code on J2ME . I am trying to encrypt data using
RSA public key on J2ME using SATSA.
I generated the public key using openssl in the PEM format and stored the
key (mypublickey) as a Base64 decoded byte array in my code.
Next, I did the following:
X509EncodedKeySpec test - new X509EncodedKeySpec(mypublickey);
KeyFactory kf = KeyFactory.getInstance("RSA");
PublicKey key = kf.generatePublic(test);
I used this key to encrypt as follows:
cipher c = Cipher.getInstance("RSA");
c.init(Cipher.ENCRYPT_MODE, key);
c.doFinal(data,0,data.length,ciphertext,0);
where byte[] data = "1234567890".getBytes();
I get no errors during this process.
Now, when I try to decrypt the string, I get a padding error as follows:
javax.crypto.BadPaddingException: Data must start with zero
The decode is done on a server.
I tried getting an instance of the cipher with RSA/ECB/NoPadding and this time the decrypt gives junk.
Question 2: The SATSA example online at http://java.sun.com/j2me/docs/satsa-dg/AppD.html
has a public key embedded as a byte array. They haven't explained how
this key is generated. Does someone know?
Question 3: Suppose, I can get the modulus and exponent of the public key is there any way I can convert it to X509EncodedKeySpec so that I can
use the APIs in SATSA?
Thanks in advance for your help. I have been trying to solve this for a lot of time and any help will be greatly appreciated.Just wanted to add my code:
public class test2 {
public static void main(String[] args) throws NoSuchAlgorithmException, InvalidKeySpecException, NoSuchPaddingException, InvalidKeyException, IllegalBlockSizeException, BadPaddingException, ShortBufferException {
// TODO Auto-generated method stub
byte [] data = "012345678901234567890123456789ab".getBytes();
Base64 base64 = new Base64();
/*public key generated by
byte [] mypublickey = base64.decode("publickey in PEM format");
byte [] ciphertext = new byte[128];
X509EncodedKeySpec test = new X509EncodedKeySpec(mypublickey);
byte [] myprivatekey = base64.decode("privatekey in pkcs8format");
KeyFactory rsakeyfac = KeyFactory.getInstance("RSA");
PublicKey pubkey = rsakeyfac.generatePublic(test);
Cipher c1 = Cipher.getInstance("RSA");
c1.init(Cipher.ENCRYPT_MODE, pubkey);
c1.doFinal(data, 0,data.length, ciphertext);
PKCS8EncodedKeySpec pks2 = new PKCS8EncodedKeySpec(myprivatekey);
RSAPrivateCrtKey privkey = (RSAPrivateCrtKey)rsakeyfac.generatePrivate(pks2);
Cipher c2 = Cipher.getInstance("RSA");
c2.init(Cipher.DECRYPT_MODE, privkey);
byte [] decrypteddata = c2.doFinal(ciphertext);
System.out.println("Decrypted String is:"+new String(decrypteddata).trim());
Error that I get is:
Exception in thread "main" javax.crypto.BadPaddingException: Data must start with zero
at sun.security.rsa.RSAPadding.unpadV15(Unknown Source)
at sun.security.rsa.RSAPadding.unpad(Unknown Source)
at com.sun.crypto.provider.RSACipher.a(DashoA13*..)
at com.sun.crypto.provider.RSACipher.engineDoFinal(DashoA13*..)
at javax.crypto.Cipher.doFinal(DashoA13*..) -
Dates in creating X.509 certificate programming without BouncyCastle sample
Thank you for the certificate programming without BouncyCastle sample.
How can I set before & after certificate dates ?There is deprecated method in the above solution...please find the updated code below
import sun.security.x509.*;
import java.security.*;
import javax.security.cert .*;
public class GenCert
public static void main(String[] args)throws Exception
CertAndKeyGen cakg = new CertAndKeyGen("RSA", "MD5WithRSA");
cakg.generate(1024);
PublicKey publicKey = cakg.getPublicKey();
System.out.println(publicKey);
PrivateKey privateKey = cakg.getPrivateKey();
System.out.println(privateKey);
X500Name name = new X500Name("One", "Two", "Three", "Four", "Five", "Six");
System.out.println(name);
//X509Cert cert = cakg.getSelfCert(name, 2000000); //deprecated
java.security.cert.X509Certificate certificate = cakg.getSelfCertificate(name,2000000);
System.out.println("cert: "+cert);
//X509Certificate certificate = X509Certificate.getInstance(cert.getSignedCert());
certificate.checkValidity();
System.out.println("Issuer DN .......... " + certificate.getIssuerDN());
System.out.println("Not after .......... " + certificate.getNotAfter());
System.out.println("Not before ......... " + certificate.getNotBefore());
System.out.println("Serial No. ......... " + certificate.getSerialNumber());
System.out.println("Signature Alg. ..... " + certificate.getSigAlgName());
System.out.println("Signature Alg. OID . " + certificate.getSigAlgOID());
System.out.println("Subject DN ......... " + certificate.getSubjectDN());
}Edited by: uglyhunK on Sep 1, 2008 9:18 PM
Edited by: uglyhunK on Sep 1, 2008 9:19 PM -
I have an RSA ACE sever and would liek to sue it for console port and VTY port access....DOES AAA support this and if so, what does the config look like...I have done it witH ACS, but would like to try it just going directly to the RSA securID server..and letting the server pop the login...and then I juts poke in my PAsscode and Token PIN...anyone done this yet....
Very simple:
1- install RSA Server on host A,
2- install ACS server on host B,
3- create an agent host on host A with host B
ip address,
4- copy the sdconf.rec file over to %Windows\system32 directory of host B,
5- install RSA agent software on host B,
6- create RSA user in host A,
7- use the RSA test utility on host B to test
authentication from host B over to host A,
8, configure ACS to use RSA SecurID. Read
the instruction on cisco web site, in the
External database,
9- run log monitor on host A RSA server,
10- try to log into a router,
11- enter the username create in step 6,
you should see that you will be able to
authenticate with RSA securID and ACS
integration.
Last but not least, if you use TACACS, you
will NOT be able to use Next-PIN mode on
RSA Server. Next-PIN mode only works with
Radius.
Easy right?
Maybe you are looking for
-
Multiple instances of the same JComponent?
I have a JCombobox which I want to display in 2 places I can not seem to do this surely I can create another JCombobox pointing to the SAME reference? but as soon as I do this the first one is removed I do not want to create it twice as I have an Act
-
Viewer plays by default instead of Canvas
Final Cut 5.1.4 My Editor may have clicked on something by mistake and I don't know how to reset it. Here's the problem: When she clicks on the Canvas after having played a clip in the Viewer, if she plays from the Spacebar, it will play the Viewer w
-
Smart Playlists aren't sorted the way I want them to be on the iPod touch.
Hello, I have two Smart Playlists that automatically adds any songs that have four/five stars. In iTunes, it's sorted alphabetically (ascending) but when I check on my iPod, it seems to be random. It wasn't like that a month ago. Anyone know what is
-
All the screen says is connect to itunes! when i do it still doesnt change
i updated my ipod lastnight, and its asking me to enable or disable location services, and then i get to a screen that says connect to itunes. ive done it all, synced it, backed it up...please help!!
-
Sound out of sync when capturing to External Hard Drive
I've been trying to capture my short film footage (5 - 60 min. mini dv tapes) on FCP without the audio getting WAY out of sync. All the footage is off. Any ideas? Here's some more info: I capture the whole 60 minutes of the tape at once. (And then I