#1
  1. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Oct 2008
    Posts
    2
    Rep Power
    0

    Java Socket Programming with AES encryption


    This is how my test program works.

    Server will encrypt some text and sends it over to the client.
    The client will then decrypts it.

    However I have some problem decrypting it. When I play around with the key and the plaintext, sometime it is able to decrypt. I think it should be some ASCII character problems.

    Right now, I am using out.writeUTF(new String(encrypted)); and on this other side I use in.readUTF() to get the string. Lastly, I convert the string to byte for decryption.

    Is there anyway to fix this problem? Basically, what and how do I send the ciphertext over and how can I decrypt properly on the other side.

    Here are my codes, thanks in advance..

    Server:
    Code:
    import java.io.*;
    import java.net.*;
    
    import java.security.*;
    import javax.crypto.*;
    import javax.crypto.spec.*;
    
    public class RealEchoServer{
        public static void main(String[] args ){
            int i = 1;
            try{
                 ServerSocket s = new ServerSocket(9003);
    
                 for (;;){
                     Socket incoming = s.accept( );
                     System.out.println("Spawning " + i);
                     new RealEchoHandler(incoming, i).start();
                     i++;
                 }
            } catch (Exception e){ System.out.println(e); }
        }
    }
    
    class RealEchoHandler extends Thread{
    	DataInputStream in;
    	DataOutputStream out;
    	private Socket incoming;
        private int counter;
    
        public RealEchoHandler(Socket i, int c){
            incoming = i;
            counter = c;
        }
    
        public void run(){
            try {
    			String key1 = "1234567812345678"; 
    	      	byte[] key2 = key1.getBytes();
    	      	SecretKeySpec secret = new SecretKeySpec(key2, "AES");
    			String msg = "Singapore Malaysia Japan India";
    			Cipher cipher = Cipher.getInstance("AES");        
    	   	 	cipher.init(Cipher.ENCRYPT_MODE, secret);
    	   		byte[] encrypted = cipher.doFinal(msg.getBytes());
    
                in = new DataInputStream(incoming.getInputStream());
    			out = new DataOutputStream(incoming.getOutputStream());
    
                boolean done = false;
                String str="";
                out.writeUTF("Connected!\n");
                out.flush();
                while (!done){
    				out.writeUTF(">");
    				out.flush();
                    str = in.readUTF();
                    System.out.println(in+":"+str);
                    if (str == null)
                        done = true;
                    else{
                    	System.out.println("Sending Ciphertext : " + new String(encrypted));
                        out.writeUTF(new String(encrypted));
                        out.flush();
                    }
                }
                incoming.close();
            }
            catch (Exception e){
            	System.out.println(e);
            }
        }
    }
    Client:
    Code:
    import java.io.*;
    import java.net.*;
    import java.security.*;
    import javax.crypto.*;
    import javax.crypto.spec.*;
    import java.util.*;
    
    class RealSocketTest{
    	public static void main(String[] args) throws NoSuchAlgorithmException, NoSuchPaddingException, InvalidKeyException, IllegalBlockSizeException, BadPaddingException{
    	
    		String str = "";
    		String str2 = "";
    		DataOutputStream out;
    		DataInputStream in;
    
    		try {
    		    Socket t = new Socket("127.0.0.1", 9003);
                in = new DataInputStream(t.getInputStream());
                out = new DataOutputStream(t.getOutputStream());
                BufferedReader br = new BufferedReader (new InputStreamReader(System.in));
    
                boolean more = true;
    			System.out.println(in.readUTF());	
    
                while (more) {
    				str = in.readUTF();
    			    System.out.print(str);
                    str2 = br.readLine();
    				out.writeUTF(str2);
                    out.flush();
    				str = in.readUTF();
    				
    				System.out.println("Encrypted Info: " + str);
    				
    				try {
    					String key1 = "1234567812345678"; 
    	      			byte[] key2 = key1.getBytes();
    	      			SecretKeySpec secret = new SecretKeySpec(key2, "AES");
    	
    					Cipher cipher = Cipher.getInstance("AES");        
    	   	 	
    					cipher.init(Cipher.DECRYPT_MODE, secret);
    					byte[] decrypted = cipher.doFinal(str.getBytes());
    					System.out.println("Decrypted Info: " + new String(decrypted));
    				}
    		        catch(BadPaddingException e){
    		        	System.out.println("Wrong Key!");
    				}
    				catch(InvalidKeyException f) {
    					System.out.println("Invalid Key!");
    				}
                }
    		} 
            catch(IOException e){
            	System.out.println("Error");
    		}
    	}
    }
  2. #2
  3. Daniel Schildsky
    Devshed Intermediate (1500 - 1999 posts)

    Join Date
    Mar 2004
    Location
    KL, Malaysia.
    Posts
    1,557
    Rep Power
    1622

    padding problem


    I think it's the well-known padding problem you're facing.

    Try hash the cipher with MD5 before sending it over the network and then dehash with MD5 again at your client side.
    Decipher the unhashed text and see if it works.
    When the programming world turns decent, the real world will turn upside down.
  4. #3
  5. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Oct 2008
    Posts
    2
    Rep Power
    0
    Hi,

    Thanks for you reply. But I thought hash is 1 way function, where there is no way to get back the plaintext from the ciphertext? is it possible to 'dehash'?

    Regards
  6. #4
  7. No Profile Picture
    Contributing User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jul 2008
    Posts
    49
    Rep Power
    13
    Ya I always thought that online md5 decrypters just took lots of different strings and hashed them then when you inputed the hash it would find an equivalent hash and tell you what string it was
  8. #5
  9. <- My daily commute :^)
    Devshed Intermediate (1500 - 1999 posts)

    Join Date
    Mar 2005
    Location
    Earth. Welcome.
    Posts
    1,501
    Rep Power
    1699
    Almost certainly your problem is that you use .readLine(). When you use readLine(), you split text into groups and the line ending character(s) is/are discarded. So basically:

    "This is a sentence.<cr, lf>This is another sentence."

    Becomes.

    stuff[0] = "This is a sentence."
    stuff[1] = "This is another sentence."

    And where are the carriage return and line feed? Poof, they're in the atmosphere.

    You need to find everyplace with a "readLine()" and instead use a non line based reader and read individual bytes.
    A -> B: Ride.

IMN logo majestic logo threadwatch logo seochat tools logo