example of java programming security

26
1 Example of Java Programming Security Developed by Garrett Colas under supervision of Dr. Janusz Zalewski Florida Gulf Coast University May 2013

Upload: others

Post on 03-Feb-2022

4 views

Category:

Documents


0 download

TRANSCRIPT

 

Example of Java Programming Security

Developed by Garrett Colas

under supervision of Dr. Janusz Zalewski

Florida Gulf Coast University

May 2013

 

1. Implementation

This example shows how to implement Message Integrity and Message Confidentiality in

Java. The sample test applications are written using the Java platform and various extensions.

The extensions used are included in JDK 1.4 base: Java Cryptography Extension (JCE), CertPath

API, Java Secure Sockets Extension (JSSE).

1.1 Message Integrity

Message digest and authentication are the first features to be implemented. Message

digest is a function that prevents any change or eavesdropping of a message by creating a very

specific signature of bits that is nearly impossible to recreate the message from. Sample code for

using message digest can be located when needed online [3]. Fig. 1 shows the output with the

digest displayed. 

 

Fig. 1 Message Digest Output

Sometimes a key is desired to allow for better verification that no tampering has occurred

when sending messages between programs. When a key is used for message digest it is then

 

referred to as message-authentication code (MAC). The process for setting up message-

authentication code can be explained in this four step process:

1. A key must be generated using the specified message-digest algorithm.

2. A MAC object should be created with the same specified message-digest algorithm.

3. The MAC object then needs to be initialized using the previously created key.

4. Finally, using the MAC object’s update method a unique plaintext string can be

generated to judge whether or not the string has been altered in any form.

When these steps are implemented in a server/client system, the MAC object’s unique

string will change if any form of eavesdropping or interloping has occurred. Fig. 2 and Fig. 3

display the output of a server/client program sending a message and checking for changes.

Fig. 2 Server MAC Output

 

 

Fig. 3 Client MAC Output

1.2 Message Confidentiality

Message confidentiality is realized through the use of private key cryptography. Plain

text is encrypted with an agreed upon key, then decrypted with that same key. The plain text is

encrypted block by block (blocks being chunks of bits, usually 64 bits long). Most likely the last

block will be short, in this case, the final block must be padded. PKCS (Public Key

Cryptographic System) is a technique for padding and is built into JDK1.4.

Three pieces of information are needed before a cipher can be used, the algorithm, mode,

and padding.

1. The Algorithm: The JDK supports a wide variety of private key algorithms, in this

example, DES(Data Encryption Standard) is used. DES was invented by IBM in the

1970s and adobted by the U.S. government as a standard. This is a 56-bit block

cipher.

 

2. The Mode: It is used to determine how encryption will work. ECB (Electronic Code

Book) is used in this example, but other modes such as IBM invented, cipher-block

chaining (CBC) or Propagating cipher-block chaining (PCBC) can be used. Other

modes have a variety of trade-offs and are better depending on what is needed.

3. Padding: This is the process of increasing the length of the last part of the message in

the final block to the block length. This could be done by adding zeros to the end of

the block, but in this implementation, the padding technique PKCS5 is used.

After the cipher is setup, a message can be encrypted and decrypted (Fig. 4).

Fig. 4 Encrypted and Decrypted Output

 

2. Test Case

The final test case addresses both message integrity and message confidentiality. The

program utilizes Message Authentication Codes for confidentiality and a private key

encryption for integrity. Figure 5 shows a brief graphical overview of the steps involved, and

Figures 6 and 7 show respective behaviors f the client and the server.

Fig. 5 Server/Client Flow Chart

 

 

Fig. 6 Secure Server Output

 

 

Fig. 7 Secure Client Output

 

Message passing steps:

1. First a server is created and waits to connect to a client.

2. After connecting to the client, the message to send is then determined.

3. The message is then encrypted, the encryption process is comprised of 5 steps:

a. Convert the message to a byte array.

b. Create and initialize a private key using the programmer selected algorithm.

c. Create and initialize the Cipher object. Three pieces of information are needed before a cipher can be used, the algorithm, mode, and padding.

d. Set the cipher to encrypt mode and using the key the message is encrypted to another byte array.

e. The message is then converted back into an array for the sending process. The encrypted message string is also used when generating the message authentication codes.

4. Using the encrypted message, a MAC key is generated. This unique key will be used to ensure that no tampering has occurred.

5. The server then sends the client 4 pieces of information.

a. The encrypted message as a string. This is used with the MAC key to check for tampering.

b. The encrypted message as a byte array. This is used with cipher when decrypting the message.

c. The cipher key, which is used to decrypted the message.

d. The MAC key, which is used to generate the MAC.

6. The server now receives a separately generated MAC, this MAC is compared with the code created at step 4.

7. Finally, with all data encrypted, sent, decrypted and both message authentication codes compared to one another, the message is displayed and the program lets the user know if the message as passed securely.

 

10 

 

3. Appendix

3.1 Message Digest

1. /* 

2.  * To change this template, choose Tools | Templates 

3.  * and open the template in the editor. 

4.  */ 

5. package secure1; 

6. import java.io.UnsupportedEncodingException; 

7. import java.security.*; 

8. import java.util.logging.Level; 

9. import java.util.logging.Logger; 

10. import javax.crypto.KeyGenerator; 

11. import javax.crypto.Mac; 

12. import javax.crypto.SecretKey; 

13. /** 

14.  * 

15.  * @author Garrett 

16.  */ 

17. public class Secure1 { 

18.     /** 

19.      * @param args the command line arguments 

20.      */ 

21.   

  public static void main(String[] args) throws UnsupportedEncodingException,NoSuchAlgorithmExc

eption, InvalidKeyException { 

22.         // 

23.         // check args and get plaintext 

24.         if (args.length != 1) { 

25.             System.err.println("Usage: java MessageDigestExample text"); 

26.             System.exit(1); 

27.         } 

28.         byte[] plainText = args[0].getBytes("UTF8"); 

29.         // 

30.         // get a message digest object using the MD5 algorithm 

31.         MessageDigest messageDigest = MessageDigest.getInstance("MD5"); 

32.         // 

33.         // print out the provider used 

11 

 

34.         System.out.println("\n" + messageDigest.getProvider().getInfo()); 

35.         // 

36.         // calculate the digest and print it out 

37.         messageDigest.update(plainText); 

38.         System.out.println("\nDigest: "); 

39.         try { 

40.             System.out.println(new String(messageDigest.digest(), "UTF8")); 

41.         } catch (UnsupportedEncodingException ex) { 

42.             Logger.getLogger(Secure1.class.getName()).log(Level.SEVERE, null, ex); 

43.         } 

44.     } 

45.     

46. } 

3.2 Server MAC

1. /* 

2.  * To change this template, choose Tools | Templates 

3.  * and open the template in the editor. 

4.  */ 

5. package secureserver; 

6.   

7. import java.io.IOException; 

8. import java.io.ObjectInputStream; 

9. import java.io.ObjectOutputStream; 

10. import java.net.ServerSocket; 

11. import java.net.Socket; 

12. import java.security.InvalidKeyException; 

13. import java.security.NoSuchAlgorithmException; 

14. import java.util.Scanner; 

15. import javax.crypto.KeyGenerator; 

16. import javax.crypto.Mac; 

17. import javax.crypto.SecretKey; 

18.   

19. /** 

20.  * 

21.  * @author Garrett 

12 

 

22.  */ 

23. public class SecureServer { 

24.   

25.     /** 

26.      * @param args the command line arguments 

27.      */ 

28.     public static void main(String[] args) throws IOException 

29.             , ClassNotFoundException, NoSuchAlgorithmException, InvalidKeyException { 

30.   

31.         // 

32.         // creating the server 

33.         // 

34.         ServerSocket server = new ServerSocket(12345, 100); 

35.         System.out.println("Server is listening at port 12345..."); 

36.         Socket connection = server.accept(); 

37.         System.out.println("A client connected."); 

38.         ObjectOutputStream output = 

39.                 new ObjectOutputStream(connection.getOutputStream()); 

40.         output.flush(); 

41.         ObjectInputStream input = 

42.                 new ObjectInputStream(connection.getInputStream()); 

43.   

44.         // 

45.         //Initialize the security objects. 

46.         // 

47.         String testMsg = "Secure Message."; 

48.         byte[] plainText = testMsg.getBytes("UTF8"); 

49.         // get a key for the HmacMD5 algorithm 

50.         System.out.println("\nStart generating key"); 

51.         KeyGenerator keyGen = KeyGenerator.getInstance("HmacMD5"); 

52.         SecretKey MD5key = keyGen.generateKey(); 

53.         System.out.println("Finish generating key"); 

54.         // get a MAC object and update it with the plaintext 

55.         Mac mac = Mac.getInstance("HmacMD5"); 

56.         mac.init(MD5key); 

57.         mac.update(plainText); 

58.         

59.         // 

60.         //Start the message exchange 

61.         // 

13 

 

62.         System.out.println("I/O streams established.");         

63.         System.out.println("‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐");     

64.         //Send the client a test message. 

65.         output.writeObject("Hello Client!"); 

66.         output.flush(); 

67.         //Receive the test message from the client. 

68.         Object obj = input.readObject(); 

69.         System.out.println("Client: " + obj); 

70.                 

71.         //Send the client the secure message text. 

72.         output.writeObject(testMsg); 

73.         output.flush(); 

74.         //Send the client the message key. 

75.         output.writeObject(MD5key); 

76.         output.flush(); 

77.         

78.         String serverMac; 

79.         String clientMac; 

80.         //Print the Mac 

81.         System.out.println("Message: " + testMsg);   

82.         System.out.println(mac.getProvider().getInfo()); 

83.         System.out.println("\nMAC: "); 

84.         System.out.println(serverMac = new String(mac.doFinal(), "UTF8")); 

85.         //Receive the clients Mac. 

86.         clientMac = input.readObject().toString(); 

87.         //Send the client the servers Mac. 

88.         output.writeObject(serverMac); 

89.         output.flush(); 

90.         

91.         //Compare the Mac values to check for tampering. 

92.         if(serverMac.equalsIgnoreCase(clientMac)) { 

93.             System.out.println("The message was sent securely."); 

94.         } else { 

95.             System.out.println("The message has been tampered with."); 

96.         } 

97.         

98.         

99.         System.out.println("‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐"); 

100.         

101.         

14 

 

102.         input.close(); 

103.         output.close(); 

104.         connection.close(); 

105.   

106.         System.out.println("Server shut down"); 

107.     } 

108. } 

3.3 Client MAC

1. /* 

2.  * To change this template, choose Tools | Templates 

3.  * and open the template in the editor. 

4.  */ 

5. package secureclient; 

6.   

7. import java.io.IOException; 

8. import java.io.ObjectInputStream; 

9. import java.io.ObjectOutputStream; 

10. import java.net.ServerSocket; 

11. import java.net.Socket; 

12. import java.security.InvalidKeyException; 

13. import java.security.NoSuchAlgorithmException; 

14. import java.util.Scanner; 

15. import javax.crypto.Mac; 

16. import javax.crypto.SecretKey; 

17.   

18. /** 

19.  * 

20.  * @author Garrett 

21.  */ 

22. public class SecureClient { 

23.   

24.     /** 

25.      * @param args the command line arguments 

26.      */ 

15 

 

27.   

  public static void main(String[] args) throws IOException, ClassNotFoundException,NoSuchAlgor

ithmException, InvalidKeyException { 

28.   

29.         // connecting to the server 

30.         System.out.println("Connecting to the server..."); 

31.         Socket client = new Socket("localhost", 12345); 

32.         System.out.println("Server connected."); 

33.         ObjectOutputStream output = 

34.                 new ObjectOutputStream(client.getOutputStream()); 

35.         output.flush(); 

36.         ObjectInputStream input = 

37.                 new ObjectInputStream(client.getInputStream()); 

38.         // 

39.         //Start the message exchange 

40.         // 

41.         System.out.println("I/O streams established."); 

42.         System.out.println("‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐"); 

43.         //Receive the test message from the server. 

44.         Object obj = input.readObject(); 

45.         System.out.println("Server: " + obj); 

46.         //Send the server a test message. 

47.         output.writeObject("Hello Server!"); 

48.         output.flush(); 

49.         //Read the secure message from server. 

50.         String secureMsg = input.readObject().toString(); 

51.         System.out.println("Server: The secure message is: " + secureMsg); 

52.         Object MD5key = input.readObject(); 

53.         // get a MAC object and update it with the text 

54.         Mac mac = Mac.getInstance("HmacMD5"); 

55.         mac.init((SecretKey)MD5key); 

56.         mac.update(secureMsg.getBytes("UTF8")); 

57.         

58.         String serverMac; 

59.         String clientMac; 

60.         //Output the Mac 

61.         System.out.println("Message: " + secureMsg);   

62.         System.out.println(mac.getProvider().getInfo()); 

63.         System.out.println("\nMAC: "); 

64.         System.out.println(clientMac = new String(mac.doFinal(), "UTF8")); 

16 

 

65.         

66.         //Send the server the clients Mac. 

67.         output.writeObject(clientMac); 

68.         output.flush(); 

69.         //Receive the servers Mac. 

70.         serverMac = input.readObject().toString(); 

71.         

72.         //Compare the Mac values to check for tampering. 

73.         if(serverMac.equalsIgnoreCase(clientMac)) { 

74.             System.out.println("The message was sent securely."); 

75.         } else { 

76.             System.out.println("The message has been tampered with."); 

77.         } 

78.         System.out.println("‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐"); 

79.         

80.         

81.         input.close(); 

82.         output.close(); 

83.         client.close(); 

84.         System.out.println("Client shut down"); 

85.     } 

86. } 

3.4 Message Confidentiality

1. package secure2crypto; 

2.   

3. import java.io.UnsupportedEncodingException; 

4. import java.security.*; 

5. import java.util.logging.Level; 

6. import java.util.logging.Logger; 

7. import javax.crypto.*; 

8. /** 

9.  * 

10.  * @author Garrett 

11.  */ 

12. public class Secure2Crypto { 

17 

 

13.   

14.     public static void main(String[] args) { 

15.         try { 

16.             String testMsg = "Hello World!";         

17.             byte[] plainText = testMsg.getBytes("UTF8"); 

18.             

19.             

20.             //DES. DES (Data Encryption Standard) was invented by IBM in the 

21.             //1970s and adopted by the U.S. government as a standard. 

22.             //It is a 56‐bit block cipher.         

23.             //Other possible private key algorithms: TripleDES, AES(Advanced Encryption 

Standard), RC2, RC4 

24.             //, RC5(RC1‐5 developed by RSA Security), Blowfish(Developed by Bruce 

Schneier 

25.             //, and PBE(Password Based Encryption)         

26.             // 

27.             // get a DES private key 

28.             //           

29.             System.out.println("\nStart generating DES key"); 

30.             KeyGenerator keyGen; 

31.             keyGen = KeyGenerator.getInstance("DES"); 

32.             keyGen.init(56); 

33.             Key key = keyGen.generateKey(); 

34.             System.out.println("Finish generating DES key"); 

35.             

36.             //ECB (Electronic Code Book) 

37.             //PKCS (Public Key Cryptographic System) 

38.             // 

39.             // get a DES cipher object and print the provider 

40.             // 

41.             //Three pieces of information are needed before a cipher can be used, 

42.             //the algorithm, mode, and padding. 

43.             Cipher cipher = Cipher.getInstance("DES/ECB/PKCS5Padding"); 

44.             System.out.println("\n" + cipher.getProvider().getInfo()); 

45.                       

46.             // 

47.             // encrypt using the key and the plaintext 

48.             // 

49.             System.out.println("\nStart encryption"); 

50.             cipher.init(Cipher.ENCRYPT_MODE, key); 

18 

 

51.             byte[] cipherText = cipher.doFinal(plainText); 

52.             System.out.println("Finish encryption: "); 

53.             System.out.println(new String(cipherText, "UTF8")); 

54.   

55.             // 

56.             // decrypt the ciphertext using the same key 

57.             // 

58.             System.out.println("\nStart decryption"); 

59.             cipher.init(Cipher.DECRYPT_MODE, key); 

60.             byte[] newPlainText = cipher.doFinal(cipherText); 

61.             System.out.println("Finish decryption: ");         

62.             System.out.println(new String(newPlainText, "UTF8")); 

63.         

64.       

  } catch (UnsupportedEncodingException | IllegalBlockSizeException | BadPaddingException |Inva

lidKeyException | NoSuchPaddingException | NoSuchAlgorithmException ex) { 

65.             Logger.getLogger(Secure2Crypto.class.getName()).log(Level.SEVERE, null, 

ex); 

66.         } 

67.     } 

68. } 

3.5 Complete Secure Server

1. package secureserver; 

2.   

3. import java.io.IOException; 

4. import java.io.ObjectInputStream; 

5. import java.io.ObjectOutputStream; 

6. import java.net.ServerSocket; 

7. import java.net.Socket; 

8. import java.security.InvalidKeyException; 

9. import java.security.Key; 

10. import java.security.NoSuchAlgorithmException; 

11. import java.util.Scanner; 

12. import java.util.logging.Level; 

13. import java.util.logging.Logger; 

14. import javax.crypto.BadPaddingException; 

15. import javax.crypto.Cipher; 

19 

 

16. import javax.crypto.IllegalBlockSizeException; 

17. import javax.crypto.KeyGenerator; 

18. import javax.crypto.Mac; 

19. import javax.crypto.NoSuchPaddingException; 

20. import javax.crypto.SecretKey; 

21.   

22. /** 

23.  * 

24.  * @author Garrett 

25.  */ 

26. public class SecureServer { 

27.   

28.     /** 

29.      * @param args the command line arguments 

30.      */ 

31.     public static void main(String[] args) throws IOException 

32.             , ClassNotFoundException, NoSuchAlgorithmException, InvalidKeyException { 

33.         try { 

34.             // creating the server 

35.             ServerSocket server = new ServerSocket(12345, 100); 

36.             System.out.println("Server is listening at port 12345..."); 

37.             

38.             //Connect to client 

39.             Socket connection = server.accept(); 

40.             System.out.println("\nA client connected."); 

41.             ObjectOutputStream output = 

42.                     new ObjectOutputStream(connection.getOutputStream()); 

43.             output.flush(); 

44.             ObjectInputStream input = 

45.                     new ObjectInputStream(connection.getInputStream()); 

46.             System.out.println("I/O streams established."); 

47.             String testMsg = "Secure Message."; 

48.             byte[] plainText = testMsg.getBytes("UTF8"); 

49.             

50.             // 

51.             // get a DES cipher object and print the provider 

52.             System.out.println("\n‐‐‐‐‐‐Encrypt Message‐‐‐‐‐‐"); 

53.             // get a DES private key         

54.             System.out.println("Start generating DES key"); 

55.             KeyGenerator DESKeyGen; 

20 

 

56.             DESKeyGen = KeyGenerator.getInstance("DES"); 

57.             DESKeyGen.init(56); 

58.             Key key = DESKeyGen.generateKey(); 

59.             System.out.println("Finish generating DES key"); 

60.   

61.             //Three pieces of information are needed before a cipher can be used, 

62.             //the algorithm, mode, and padding. 

63.             Cipher cipher = Cipher.getInstance("DES/ECB/PKCS5Padding"); 

64.             System.out.println("\n" + cipher.getProvider().getInfo()); 

65.   

66.   

67.             // encrypt using the key and the plaintext 

68.             System.out.println("\nStart encryption"); 

69.             cipher.init(Cipher.ENCRYPT_MODE, key); 

70.             byte[] cipherText = cipher.doFinal(plainText); 

71.             String cipherString = cipherText.toString(); 

72.             System.out.println("Finish encryption: "); 

73.             //System.out.println(new String(cipherText, "UTF8")); 

74.             System.out.println(cipherString); 

75.             System.out.println("‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐"); 

76.             

77.             

78.             System.out.println("\n‐‐‐‐‐‐Initializing MAC Key‐‐‐‐‐‐");         

79.             // get a key for the HmacMD5 algorithm 

80.             System.out.println("Start generating key..."); 

81.             KeyGenerator keyGen = KeyGenerator.getInstance("HmacMD5"); 

82.             SecretKey MD5key = keyGen.generateKey(); 

83.             System.out.println("Finished generating key."); 

84.             // get a MAC object and update it with the plaintext 

85.             Mac mac = Mac.getInstance("HmacMD5"); 

86.             mac.init(MD5key); 

87.             //mac.update(plainText); 

88.             mac.update(cipherString.getBytes()); 

89.             System.out.println("‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐"); 

90.             

91.             // 

92.             //Start the message exchange 

93.             //   

94.             System.out.println("\n‐‐‐‐‐‐Message Exchange‐‐‐‐‐‐"); 

95.             //Send the client a test message. 

21 

 

96.             output.writeObject("Hello Client!"); 

97.             output.flush(); 

98.             //Receive the test message from the client. 

99.             Object obj = input.readObject(); 

100.             System.out.println("Client: " + obj);   

101.             System.out.println("Sending client the msg and key..."); 

102.             //Send the client the secure message text. 

103.             //output.writeObject(testMsg); 

104.             output.writeObject(cipherString); 

105.             output.flush(); 

106.             output.writeObject(cipherText); 

107.             output.flush(); 

108.             

109.             //output.writeObject(cipher); 

110.             //output.flush(); 

111.             output.writeObject(key); 

112.             output.flush(); 

113.             //Send the client the message key. 

114.             output.writeObject(MD5key); 

115.             output.flush(); 

116.             System.out.println("‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐"); 

117.         

118.   

119.             //Print the Mac (The message and resulting MAC data) 

120.             System.out.println("\n‐‐‐‐‐‐Message Information‐‐‐‐‐‐"); 

121.             System.out.println("Message: " + testMsg);   

122.             System.out.println("Encrpyted Message: " + cipherText.toString()); 

123.             System.out.println(mac.getProvider().getInfo()); 

124.             System.out.println("\nMAC: "); 

125.             String serverMac = new String(mac.doFinal(), "UTF8"); 

126.             System.out.println(serverMac); 

127.             //Receive the clients Mac. 

128.             String clientMac = input.readObject().toString(); 

129.             //Send the client the servers Mac. 

130.             output.writeObject(serverMac); 

131.             output.flush(); 

132.             System.out.println("‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐"); 

133.             

134.             System.out.println("\n‐‐‐‐‐‐Decrypt Message‐‐‐‐‐‐"); 

135.             System.out.println("\n" + cipher.getProvider().getInfo()); 

22 

 

136.             System.out.println("\nStart decryption"); 

137.             cipher.init(Cipher.DECRYPT_MODE, key); 

138.             byte[] newPlainText = cipher.doFinal(cipherText); 

139.             System.out.println("Finish decryption: "); 

140.             System.out.println(new String(newPlainText, "UTF8")); 

141.             System.out.println("‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐"); 

142.             

143.             //Finish sending the message by checking integrity. 

144.             //Compare the Mac values to check for tampering. 

145.             System.out.println("\n‐‐‐‐‐‐Message Results‐‐‐‐‐‐"); 

146.             if(serverMac.equalsIgnoreCase(clientMac)) { 

147.                 System.out.println("The message was sent securely."); 

148.             } else { 

149.                 System.out.println("The message has been tampered with."); 

150.             }         

151.             System.out.println("‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐"); 

152.             

153.             //Close I/O and connection 

154.             input.close(); 

155.             output.close(); 

156.             connection.close(); 

157.   

158.             System.out.println("\nServer shut down"); 

159.         } catch (IllegalBlockSizeException ex) { 

160.             Logger.getLogger(SecureServer.class.getName()).log(Level.SEVERE, null, ex); 

161.         } catch (BadPaddingException ex) { 

162.             Logger.getLogger(SecureServer.class.getName()).log(Level.SEVERE, null, ex); 

163.         } catch (NoSuchPaddingException ex) { 

164.             Logger.getLogger(SecureServer.class.getName()).log(Level.SEVERE, null, ex); 

165.         } 

166.     } 

167. } 

3.6 Complete Secure Client

1. package secureclient; 

2.   

3. import java.io.IOException; 

4. import java.io.ObjectInputStream; 

23 

 

5. import java.io.ObjectOutputStream; 

6. import java.net.ServerSocket; 

7. import java.net.Socket; 

8. import java.security.InvalidKeyException; 

9. import java.security.Key; 

10. import java.security.NoSuchAlgorithmException; 

11. import java.util.Scanner; 

12. import java.util.logging.Level; 

13. import java.util.logging.Logger; 

14. import javax.crypto.BadPaddingException; 

15. import javax.crypto.Cipher; 

16. import javax.crypto.IllegalBlockSizeException; 

17. import javax.crypto.KeyGenerator; 

18. import javax.crypto.Mac; 

19. import javax.crypto.NoSuchPaddingException; 

20. import javax.crypto.SecretKey; 

21.   

22. /** 

23.  * 

24.  * @author Garrett 

25.  */ 

26. public class SecureClient { 

27.   

28.     /** 

29.      * @param args the command line arguments 

30.      */ 

31.   

  public static void main(String[] args) throws IOException, ClassNotFoundException,NoSuchAlgor

ithmException, InvalidKeyException { 

32.         try { 

33.             // connecting to the server 

34.             System.out.println("Connecting to the server..."); 

35.             Socket client = new Socket("localhost", 12345); 

36.             System.out.println("Server connected."); 

37.             ObjectOutputStream output = 

38.                     new ObjectOutputStream(client.getOutputStream()); 

39.             output.flush(); 

40.             ObjectInputStream input = 

41.                     new ObjectInputStream(client.getInputStream()); 

42.             System.out.println("I/O streams established."); 

24 

 

43.   

44.             // 

45.             //Start the message exchange 

46.             // 

47.             System.out.println("\n‐‐‐‐‐‐Message Exchange‐‐‐‐‐‐"); 

48.             //Receive the test message from the server. 

49.             Object obj = input.readObject(); 

50.             System.out.println("Server: " + obj); 

51.             //Send the server a test message. 

52.             output.writeObject("Hello Server!"); 

53.             output.flush(); 

54.   

55.             //Read the secure message from server.(Used to generate MAC) 

56.             String secureMsg = input.readObject().toString(); 

57.             System.out.println("Server: The received message is, " + secureMsg); 

58.   

59.             //Read the raw cipher text from the server 

60.             byte[] cipherText = (byte[]) input.readObject(); 

61.             //Read key from server 

62.             Key key = (Key) input.readObject(); 

63.             Cipher cipher = Cipher.getInstance("DES/ECB/PKCS5Padding"); 

64.             

65.             //Read the MAC key from the server 

66.             Object MD5key = input.readObject(); 

67.             System.out.println("‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐"); 

68.   

69.             

70.             

71.             System.out.println("\n‐‐‐‐‐‐Decrypt Message‐‐‐‐‐‐"); 

72.             System.out.println("\n" + cipher.getProvider().getInfo()); 

73.             System.out.println("\nStart decryption"); 

74.             cipher.init(Cipher.DECRYPT_MODE, key); 

75.             byte[] newPlainText = cipher.doFinal(cipherText); 

76.             System.out.println("Finish decryption: "); 

77.             String finalMsg = new String(newPlainText, "UTF8"); 

78.             System.out.println(finalMsg); 

79.             System.out.println("‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐"); 

80.       

81.             

82.             

25 

 

83.             

84.             System.out.println("\n‐‐‐‐‐‐Message Information‐‐‐‐‐‐"); 

85.             // get a MAC object and update it with the text 

86.             Mac mac = Mac.getInstance("HmacMD5"); 

87.             mac.init((SecretKey) MD5key); 

88.             mac.update(secureMsg.getBytes("UTF8")); 

89.             //Output the Mac 

90.             System.out.println("Message: " + secureMsg); 

91.             System.out.println("Decrpyted Message: " + finalMsg); 

92.             System.out.println(mac.getProvider().getInfo()); 

93.             System.out.println("\nMAC: "); 

94.             String clientMac = new String(mac.doFinal(), "UTF8"); 

95.             System.out.println(clientMac); 

96.             //Send the server the clients Mac. 

97.             output.writeObject(clientMac); 

98.             output.flush(); 

99.             //Receive the servers Mac. 

100.             String serverMac = input.readObject().toString(); 

101.             System.out.println("‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐"); 

102.   

103.             

104.             

105.             

106.             System.out.println("\n‐‐‐‐‐‐Message Results‐‐‐‐‐‐"); 

107.             //Compare the Mac values to check for tampering. 

108.             if (serverMac.equalsIgnoreCase(clientMac)) { 

109.                 System.out.println("The message was sent securely."); 

110.             } else { 

111.                 System.out.println("The message has been tampered with."); 

112.             } 

113.             System.out.println("‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐"); 

114.   

115.   

116.             

117.             

118.             input.close(); 

119.             output.close(); 

120.             client.close(); 

121.             System.out.println("\nClient shut down"); 

122.         } catch (NoSuchPaddingException ex) { 

26 

 

123.             Logger.getLogger(SecureClient.class.getName()).log(Level.SEVERE, null, ex); 

124.         } catch (IllegalBlockSizeException ex) { 

125.             Logger.getLogger(SecureClient.class.getName()).log(Level.SEVERE, null, ex); 

126.         } catch (BadPaddingException ex) { 

127.             Logger.getLogger(SecureClient.class.getName()).log(Level.SEVERE, null, ex); 

128.         } 

129.     } 

130. }