Solved

Encryption/decryption of password.

Posted on 2004-09-16
19
4,647 Views
Last Modified: 2008-02-07
Hi,

    I am having problem with password encryption/decryption. I can successfully encrypt but when I do the decryption I am getting few exceptions like IllegalBlockSizeException, BadPaddingException. Below is the code which I have written and the exception I am getting when I am decrypting the encrypted password.


import java.security.*;
import javax.crypto.*;
import javax.crypto.spec.*;
import java.util.*;
import java.io.*;

public class PwdEncryption
{
   
    Cipher ecipher;
    Cipher dcipher;
    SecretKey key                       = null;
    KeyGenerator desKeyGen;    
   
    protected static String KEYGEN_STR = "";
   
   
    public PwdEncryption()
    {
        try
        {
            KeyGenerator keyGen = KeyGenerator.getInstance("DES");
            SecretKey desSecretKey = keyGen.generateKey();
            byte[] bytes = desSecretKey.getEncoded();
            DataInputStream dis = null;            
            try
            {
                FileInputStream fis = new FileInputStream("C:/usr3/devl/env/ant/DESKey.txt");
                BufferedInputStream bis = new BufferedInputStream(fis);
                dis = new DataInputStream(bis);
                int count = 0;
                String result = null;
                StringBuffer buf = new StringBuffer();
               
                while((result = dis.readLine()) != null)
                {
                    buf.append(result);
                    count++;
                }                
                KEYGEN_STR = buf.toString();                
            }
            catch(FileNotFoundException ex)
            {   }
            finally
            {
                if(dis != null)
                {
                    try
                    {
                        dis.close();
                    }
                    catch (IOException ioe)
                    {  }
                }                
            }
        }
        catch(Exception ex)
        {
            ex.printStackTrace();
        }
    }
   
    private Key getKey()
    {
        try
        {
            byte[] bytes = getbytes(KEYGEN_STR);
            DESKeySpec pass = new DESKeySpec(bytes);
           
            SecretKeyFactory sKeyFactory = SecretKeyFactory.getInstance("DES");
            SecretKey sKey = sKeyFactory.generateSecret(pass);

            return sKey;
        }
        catch(Exception ex)
        {
            ex.printStackTrace();
        }
        return null;
    }
   
    private byte[] getbytes(String str)
    {
        ByteArrayOutputStream byteOutputStream = new ByteArrayOutputStream();
       
        StringTokenizer sTokenizer = new StringTokenizer(str, "-", false);
        while(sTokenizer.hasMoreTokens())
        {
            try
            {
                byteOutputStream.write(sTokenizer.nextToken().getBytes());
            }
            catch(IOException ex)
            {
            }
        }
       
        byteOutputStream.toByteArray());
        return byteOutputStream.toByteArray();
    }
   

    public String encrypt(String sourceStr)
    {        
        try
        {
            // Get secret key
            Key key = getKey();
             
            ecipher = Cipher.getInstance("DES/ECB/PKCS5Padding");
            ecipher.init(Cipher.ENCRYPT_MODE, key);            
           
            byte[] enc = ecipher.doFinal((new String(sourceStr)).getBytes("UTF-8"));
           
             // Encode bytes to base64 to get a string
            return new sun.misc.BASE64Encoder().encode(enc);            

        }
        catch(Exception ex)
        {
            ex.printStackTrace();
        }
        return null;
    }
   
   
    public String decrypt(String sourceStr)
    {
        try
        {
            // Get secret key
            Key key = getKey();
           
            dcipher = Cipher.getInstance("DES/ECB/PKCS5Padding");                      
            dcipher.init(Cipher.DECRYPT_MODE, key);            
           
            // Decode base64 to get bytes
            byte[] dec = new sun.misc.BASE64Decoder().decodeBuffer(sourceStr);
           
            //Decrypt data in a single step
           
            byte[] utf8 = dcipher.doFinal(dec);
         
            // Decode using utf-8
            return new String(utf8, "UTF-8");
        }
        catch(Exception ex)
        {
            ex.printStackTrace();
        }
        return null;
    }      
}


javax.crypto.IllegalBlockSizeException: Input length (with padding) not multiple of 8 bytes
      at com.sun.crypto.provider.SunJCE_h.a(DashoA6275)
      at com.sun.crypto.provider.SunJCE_h.b(DashoA6275)
      at com.sun.crypto.provider.SunJCE_h.b(DashoA6275)
      at com.sun.crypto.provider.DESCipher.engineDoFinal(DashoA6275)
      at javax.crypto.Cipher.doFinal(DashoA6275)



Can anyone please help me with the code so that it would work. It is very urgent.



Thanks


0
Comment
Question by:sunny08
  • 12
  • 6
19 Comments
 
LVL 86

Expert Comment

by:CEHJ
ID: 12078340
Passwords should not actually be stored in an encrypted form as this is weak security. They should be stored as one-way hashed values then the entered cleartext should have its hash calculated and compared to the stored password.
0
 
LVL 14

Expert Comment

by:sudhakar_koundinya
ID: 12078363
I see some problems with ur code.

But here is how I did in my last project. Using the example I get from www.javaalmanac.com

Regards
Sudhakar


import java.security.*;
import java.security.spec.*;
import javax.crypto.*;
import javax.crypto.spec.*;
import java.util.*;
import java.io.*;


class PasswrdEncryption {
    Cipher ecipher;
    Cipher dcipher;
   
    // 8-byte Salt
    byte[] salt = {
        (byte)0xA9, (byte)0x9B, (byte)0xC8, (byte)0x32,
        (byte)0x56, (byte)0x35, (byte)0xE3, (byte)0x03
    };
   
    // Iteration count
    int iterationCount = 19;
   
    PasswrdEncryption(String passPhrase) {
        try {
            // Create the key
            KeySpec keySpec = new PBEKeySpec(passPhrase.toCharArray(), salt, iterationCount);
            SecretKey key = SecretKeyFactory.getInstance(
            "PBEWithMD5AndDES").generateSecret(keySpec);
            ecipher = Cipher.getInstance(key.getAlgorithm());
            dcipher = Cipher.getInstance(key.getAlgorithm());
           
            // Prepare the parameter to the ciphers
            AlgorithmParameterSpec paramSpec = new PBEParameterSpec(salt, iterationCount);
           
            // Create the ciphers
            ecipher.init(Cipher.ENCRYPT_MODE, key, paramSpec);
            dcipher.init(Cipher.DECRYPT_MODE, key, paramSpec);
        } catch (java.security.InvalidAlgorithmParameterException e) {
        } catch (java.security.spec.InvalidKeySpecException e) {
        } catch (javax.crypto.NoSuchPaddingException e) {
        } catch (java.security.NoSuchAlgorithmException e) {
        } catch (java.security.InvalidKeyException e) {
        }
    }
   
    public String encrypt(String str) {
        try {
            // Encode the string into bytes using utf-8
            byte[] utf8 = str.getBytes("UTF8");
           
            // Encrypt
            byte[] enc = ecipher.doFinal(utf8);
           
            // Encode bytes to base64 to get a string
            return new sun.misc.BASE64Encoder().encode(enc);
        } catch (javax.crypto.BadPaddingException e) {
        } catch (IllegalBlockSizeException e) {
        } catch (UnsupportedEncodingException e) {
        } catch (java.io.IOException e) {
        }
        return null;
    }
   
    public String decrypt(String str) {
        try {
            // Decode base64 to get bytes
            byte[] dec = new sun.misc.BASE64Decoder().decodeBuffer(str);
           
            // Decrypt
            byte[] utf8 = dcipher.doFinal(dec);
           
            // Decode using utf-8
            return new String(utf8, "UTF8");
        } catch (javax.crypto.BadPaddingException e) {
        } catch (IllegalBlockSizeException e) {
        } catch (UnsupportedEncodingException e) {
        } catch (java.io.IOException e) {
        }
        return null;
    }
   
   
    public static void main(String s[]) {
        // Here is an example that uses the class
        try {
            // Create encrypter/decrypter class
            String strKey=loadKey("c:\\mykey.key");
            System.err.println("My Key :"+strKey);
            PasswrdEncryption encrypter = new PasswrdEncryption(strKey);
           
            // Encrypt
            String encrypted = encrypter.encrypt("This is my password");
            System.err.println("Ecnrypted String: "+ encrypted)
            ;
            PasswrdEncryption encrypter1 = new PasswrdEncryption(strKey);
            // Decrypt
            String decrypted = encrypter1.decrypt(encrypted);
            System.err.println("Decrypted String: "+ decrypted);
        } catch (Exception e) {
        }
    }
   
    public static String loadKey(String file) {
        try {
            FileInputStream fin=new FileInputStream(file);
            int byteCount=fin.available();
            byte array[]=new byte[byteCount];
            fin.read(array);
            return new String(array);
        }
        catch(Exception ex) {
            return "";
        }
       
       
    }
}

0
 
LVL 14

Expert Comment

by:sudhakar_koundinya
ID: 12078432
>> FileInputStream fis = new FileInputStream("C:/usr3/devl/env/ant/DESKey.txt");

OK, I didn't see that you are using the file

I tested ur code again and found working fine at my end

for what key and what password u are getting the error??
0
 

Author Comment

by:sunny08
ID: 12078855
Hi,

   Thanks for ur quick response. I wonder how it is working on ur end. I am using DES algorithm for generating the key. Here is the thing, I am encrypting the password, saving in the database and then while retrieving decrypting the password. When I am decrypting the password I am getting errors.


Thanks

0
 
LVL 14

Accepted Solution

by:
sudhakar_koundinya earned 500 total points
ID: 12079037
OK

Check if encrypted string correctly stored into database. I doubt that.

Check also What is the size of ur database column
0
 

Author Comment

by:sunny08
ID: 12084676
yeah I was wondering why it is working on ur end and not at my end. I thought the same thing tried to execute from command prompt, it was working fine, then I thought it might be the column size. After seeing ur comment, i am sure it is the size of the column.

Thanks for the response
   
0
 
LVL 14

Expert Comment

by:sudhakar_koundinya
ID: 12085082
Glad to help

Thanks for Accepting :-)
0
 

Author Comment

by:sunny08
ID: 12112689
Hi sudhakar,
 
           As we came to conclusion that it might be the size of the column, I increased the size of the column. But still I am getting the same errors while decrypting. Can u please help me out with this one.


Thanks
0
 
LVL 14

Expert Comment

by:sudhakar_koundinya
ID: 12121150
OK let me know,

what is the database column size and database u are using for ur application?

I will try to find the solution

Mean while did you try with my code??  Let me know if you get problems with my code too

Regards
Sudhakar
0
Free Trending Threat Insights Every Day

Enhance your security with threat intelligence from the web. Get trending threat insights on hackers, exploits, and suspicious IP addresses delivered to your inbox with our free Cyber Daily.

 

Author Comment

by:sunny08
ID: 12124055
I have observed one thing today. When I encrypt the password and save to the database and just after that print the decrypted password of that saved password, then decrypt is working fine. But when I retrieve the saved pwd from database and decrypt it is giving error.
Below is the code which works :

             PwdEncryption pwdEncryption = new PwdEncryption();            
             String encryptedPwd = pwdEncryption.encrypt(m_NewPasswordFld.getValue());            
            System.out.println("encyptedPwd :::::::::::" + encryptedPwd + " LENGTH = " + encryptedPwd.length());
           
            // Set user password
            m_User.setPassword(encryptedPwd);

            System.out.println("decryptedPwd :::::::::" + pwdEncryption.decrypt(encyptedPwd));

and when I try to decrypt the database pwd which is encrypted, below is the code :

PwdEncryption pwdEncryption = new PwdEncryption();
usrPassword = pwdEncryption.decrypt(usrPassword); // usrPassword is the password from the DB which was encrypted and saved
System.out.println("usrPassword after decrypt = " + usrPassword);

and the error is :

javax.crypto.IllegalBlockSizeException: Input length (with padding) not multiple of 8 bytes
      at com.sun.crypto.provider.SunJCE_h.a(DashoA6275)
      at com.sun.crypto.provider.SunJCE_h.b(DashoA6275)
      at com.sun.crypto.provider.SunJCE_h.b(DashoA6275)
      at com.sun.crypto.provider.DESCipher.engineDoFinal(DashoA6275)
      at javax.crypto.Cipher.doFinal(DashoA6275)

We are using Informix and the column size is 25.

Let me know.

Thanks

0
 
LVL 14

Expert Comment

by:sudhakar_koundinya
ID: 12124756
>>We are using Informix and the column size is 25.

What is the maximum password length you are giving from web page??

if  it is more than 8 try increasing the column size. It will solve your problem

Regards
Sudhakar


0
 
LVL 14

Expert Comment

by:sudhakar_koundinya
ID: 12124934
when u are using such type of algorithms for password encryption, the size of encrypted is unpredictable. So I suggest you to increase the column size to 100 and test it.
0
 
LVL 14

Expert Comment

by:sudhakar_koundinya
ID: 12125750
The output what you are getting  from the database is wrong  or the string what you are inserting is not getting stored correctly. Check it again


Regards
Sudhakar
0
 

Author Comment

by:sunny08
ID: 12126712
I tried every possible way but in vain. I tried using ur code. I see that u have a method called loadkey(), so what r u generating in that the file. Is it a key, if it is a key then which algorithm r u using or something else. Could u please tell me.
0
 
LVL 14

Expert Comment

by:sudhakar_koundinya
ID: 12126739
loadkey  just gets the string from a file
0
 
LVL 14

Expert Comment

by:sudhakar_koundinya
ID: 12127023
It is Encrypting with DES Using a Pass Phrase
0
 

Author Comment

by:sunny08
ID: 12127296
what is the string in the file? can u tell me how u r generating the string. can u send me that.


Thanks
0
 
LVL 14

Expert Comment

by:sudhakar_koundinya
ID: 12127379
I just put this

This is my key to encrypt my password
0
 
LVL 14

Expert Comment

by:sudhakar_koundinya
ID: 12127399
In other words the method is like this

 public static String loadKey() {
  retiurn "This is my key to encrypt my password";
 
       
    }
0

Featured Post

How to run any project with ease

Manage projects of all sizes how you want. Great for personal to-do lists, project milestones, team priorities and launch plans.
- Combine task lists, docs, spreadsheets, and chat in one
- View and edit from mobile/offline
- Cut down on emails

Join & Write a Comment

After being asked a question last year, I went into one of my moods where I did some research and code just for the fun and learning of it all.  Subsequently, from this journey, I put together this article on "Range Searching Using Visual Basic.NET …
By the end of 1980s, object oriented programming using languages like C++, Simula69 and ObjectPascal gained momentum. It looked like programmers finally found the perfect language. C++ successfully combined the object oriented principles of Simula w…
Viewers will learn about arithmetic and Boolean expressions in Java and the logical operators used to create Boolean expressions. We will cover the symbols used for arithmetic expressions and define each logical operator and how to use them in Boole…
This tutorial covers a practical example of lazy loading technique and early loading technique in a Singleton Design Pattern.

706 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question

Need Help in Real-Time?

Connect with top rated Experts

20 Experts available now in Live!

Get 1:1 Help Now