KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > mx4j > tools > adaptor > ssl > SSLAdaptorServerSocketFactory


1 /*
2  * Copyright (C) The MX4J Contributors.
3  * All rights reserved.
4  *
5  * This software is distributed under the terms of the MX4J License version 1.0.
6  * See the terms of the MX4J License in the documentation provided with this software.
7  */

8
9 package mx4j.tools.adaptor.ssl;
10
11 import java.io.File JavaDoc;
12 import java.io.FileInputStream JavaDoc;
13 import java.io.IOException JavaDoc;
14 import java.io.InputStream JavaDoc;
15 import java.net.InetAddress JavaDoc;
16 import java.net.ServerSocket JavaDoc;
17 import java.security.KeyStore JavaDoc;
18 import java.security.Provider JavaDoc;
19 import java.security.Security JavaDoc;
20 import java.security.UnrecoverableKeyException JavaDoc;
21 import javax.net.ssl.SSLServerSocket;
22 import javax.net.ssl.SSLServerSocketFactory;
23
24 import com.sun.net.ssl.KeyManagerFactory;
25 import com.sun.net.ssl.SSLContext;
26 import com.sun.net.ssl.TrustManagerFactory;
27 import mx4j.log.Log;
28 import mx4j.log.Logger;
29
30 /**
31  * TODO: Fix this class to avoid hardcoding Sun's provider, since it will not work with IBM's JDK.
32  * This MBean creates SSLServerSocket instances. <p>
33  * It can be configured to use a specific keystore and SSL protocol version to create SSLServerSockets
34  * that will use the keystore information to encrypt data. <br>
35  * <p/>
36  * A keystore can be created with this command:
37  * <pre>
38  * keytool -genkey -v -keystore store.key -storepass storepwd -keypass keypwd -dname "CN=Simone Bordet, OU=Project Administrator, O=MX4J, L=Torino, S=TO, C=IT" -validity 365
39  * </pre>
40  * or with this minimal command (that will prompt you for further information):
41  * <pre>
42  * keytool -genkey -keystore store.key
43  * </pre>
44  * <p/>
45  * A keystore may contains more than one entry, but only the first entry will be used
46  * for encryption, no matter which is the alias for that entry.
47  * <p/>
48  * Following the first example of generation of the keystore, this MBean must be instantiated and then setup by
49  * invoking the following methods:
50  * <ul>
51  * <li> {@link #setKeyStoreName}("store.key");
52  * <li> {@link #setKeyStorePassword}("storepwd");
53  * <li> {@link #setKeyManagerPassword}("keypwd");
54  * </ul>
55  * before {@link #createServerSocket} is called.
56  *
57  * @version $Revision: 1.5 $
58  */

59 public class SSLAdaptorServerSocketFactory implements SSLAdaptorServerSocketFactoryMBean
60 {
61    static
62    {
63       addProvider(new com.sun.net.ssl.internal.ssl.Provider());
64    }
65
66    private String JavaDoc m_keyStoreType = "JKS";
67    private String JavaDoc m_trustStoreType = "JKS";
68    private String JavaDoc m_keyStoreName;
69    private String JavaDoc m_trustStoreName;
70    private String JavaDoc m_keyStorePassword;
71    private String JavaDoc m_trustStorePassword;
72    private String JavaDoc m_keyManagerAlgorithm = "SunX509";
73    private String JavaDoc m_trustManagerAlgorithm = "SunX509";
74    private String JavaDoc m_keyManagerPassword;
75    private String JavaDoc m_sslProtocol = "TLS";
76
77    public static void addProvider(Provider JavaDoc provider)
78    {
79       Security.addProvider(provider);
80    }
81
82    public void setKeyStoreType(String JavaDoc keyStoreType)
83    {
84       if (keyStoreType == null || keyStoreType.trim().length() == 0)
85       {
86          throw new IllegalArgumentException JavaDoc("Invalid KeyStore type");
87       }
88       m_keyStoreType = keyStoreType;
89    }
90
91    public void setTrustStoreType(String JavaDoc trustStoreType)
92    {
93       if (trustStoreType == null || trustStoreType.trim().length() == 0)
94       {
95          throw new IllegalArgumentException JavaDoc("Invalid TrustStore type");
96       }
97       m_trustStoreType = trustStoreType;
98    }
99
100    public void setKeyStoreName(String JavaDoc name)
101    {
102       if (name == null || name.trim().length() == 0)
103       {
104          throw new IllegalArgumentException JavaDoc("Invalid KeyStore name");
105       }
106       m_keyStoreName = name;
107    }
108
109    public void setTrustStoreName(String JavaDoc name)
110    {
111       if (name == null || name.trim().length() == 0)
112       {
113          throw new IllegalArgumentException JavaDoc("Invalid TrustStore name");
114       }
115       m_trustStoreName = name;
116    }
117
118    public void setKeyStorePassword(String JavaDoc password)
119    {
120       if (password == null || password.trim().length() == 0)
121       {
122          throw new IllegalArgumentException JavaDoc("Invalid KeyStore password");
123       }
124       m_keyStorePassword = password;
125    }
126
127    public void setTrustStorePassword(String JavaDoc password)
128    {
129       if (password == null || password.trim().length() == 0)
130       {
131          throw new IllegalArgumentException JavaDoc("Invalid TrustStore password");
132       }
133       m_trustStorePassword = password;
134    }
135
136    public void setKeyManagerAlgorithm(String JavaDoc algorithm)
137    {
138       if (algorithm == null || algorithm.trim().length() == 0)
139       {
140          throw new IllegalArgumentException JavaDoc("Invalid KeyManager algorithm");
141       }
142       m_keyManagerAlgorithm = algorithm;
143    }
144
145    public void setTrustManagerAlgorithm(String JavaDoc algorithm)
146    {
147       if (algorithm == null || algorithm.trim().length() == 0)
148       {
149          throw new IllegalArgumentException JavaDoc("Invalid TrustManager algorithm");
150       }
151       m_trustManagerAlgorithm = algorithm;
152    }
153
154    public void setKeyManagerPassword(String JavaDoc password)
155    {
156       if (password == null || password.trim().length() == 0)
157       {
158          throw new IllegalArgumentException JavaDoc("Invalid KeyManager password");
159       }
160       m_keyManagerPassword = password;
161    }
162
163    public void setSSLProtocol(String JavaDoc protocol)
164    {
165       if (protocol == null || protocol.trim().length() == 0)
166       {
167          throw new IllegalArgumentException JavaDoc("Invalid SSL protocol");
168       }
169       m_sslProtocol = protocol;
170    }
171
172    /**
173     * Returns a SSLServerSocket on the given port.
174     */

175    public ServerSocket JavaDoc createServerSocket(int port, int backlog, String JavaDoc host) throws IOException JavaDoc
176    {
177       if (m_keyStoreName == null)
178       {
179          throw new IOException JavaDoc("KeyStore file name cannot be null");
180       }
181       if (m_keyStorePassword == null)
182       {
183          throw new IOException JavaDoc("KeyStore password cannot be null");
184       }
185
186       Logger logger = getLogger();
187       if (logger.isEnabledFor(Logger.TRACE))
188       {
189          logger.trace("Creating SSLServerSocket");
190          logger.trace("\tKeyStore " + m_keyStoreName + ", type " + m_keyStoreType);
191          logger.trace("\tKeyManager algorithm is " + m_keyManagerAlgorithm);
192          logger.trace("\tTrustStore " + m_trustStoreName + ", type " + m_trustStoreType);
193          logger.trace("\tTrustManager algorithm is " + m_trustManagerAlgorithm);
194          logger.trace("\tSSL protocol version is " + m_sslProtocol);
195       }
196
197       try
198       {
199          KeyStore JavaDoc keystore = KeyStore.getInstance(m_keyStoreType);
200          InputStream JavaDoc keyStoreStream = getClass().getClassLoader().getResourceAsStream(m_keyStoreName);
201          // Must check for nullity, otherwise a new empty keystore is created by KeyStore.load
202
if (keyStoreStream == null)
203          {
204             // Let's look at the file system, maybe that the name provided is in fact a file path
205
File JavaDoc fle = new java.io.File JavaDoc(m_keyStoreName);
206             if (fle.exists()) keyStoreStream = new FileInputStream JavaDoc(fle);
207          }
208          if (keyStoreStream == null) throw new IOException JavaDoc("Cannot find KeyStore " + m_keyStoreName);
209          keystore.load(keyStoreStream, m_keyStorePassword.toCharArray());
210          try
211          {
212             keyStoreStream.close();
213          }
214          catch (IOException JavaDoc x)
215          {
216          }
217
218          KeyManagerFactory keyFactory = KeyManagerFactory.getInstance(m_keyManagerAlgorithm);
219          // Use the keystore password as default if not given
220
keyFactory.init(keystore, m_keyManagerPassword == null ? m_keyStorePassword.toCharArray() : m_keyManagerPassword.toCharArray());
221
222          TrustManagerFactory trustFactory = null;
223          if (m_trustStoreName != null)
224          {
225             // User specified a trust store, retrieve it
226

227             if (m_trustStorePassword == null)
228             {
229                throw new IOException JavaDoc("TrustStore password cannot be null");
230             }
231
232             KeyStore JavaDoc trustStore = KeyStore.getInstance(m_trustStoreType);
233             InputStream JavaDoc trustStoreStream = getClass().getClassLoader().getResourceAsStream(m_trustStoreName);
234             // Check for nullity
235
if (trustStoreStream == null)
236             {
237                throw new IOException JavaDoc("Cannot find TrustStore " + m_trustStoreName);
238             }
239             trustStore.load(trustStoreStream, m_trustStorePassword.toCharArray());
240
241             trustFactory = TrustManagerFactory.getInstance(m_trustManagerAlgorithm);
242             trustFactory.init(trustStore);
243          }
244
245          SSLContext context = SSLContext.getInstance(m_sslProtocol);
246          // Below call does not handle TrustManagers, needed when server must authenticate clients.
247
context.init(keyFactory.getKeyManagers(), trustFactory == null ? null : trustFactory.getTrustManagers(), null);
248
249          SSLServerSocketFactory ssf = context.getServerSocketFactory();
250          SSLServerSocket serverSocket = (SSLServerSocket)ssf.createServerSocket(port, backlog, InetAddress.getByName(host));
251
252          return serverSocket;
253       }
254       catch (IOException JavaDoc x)
255       {
256          logger.error("", x);
257          throw x;
258       }
259       catch (UnrecoverableKeyException JavaDoc x)
260       {
261          // Wrong password for the key
262
logger.error("Probably a bad key password", x);
263          throw new IOException JavaDoc("Probably a bad key password: " + x.toString());
264       }
265       catch (Exception JavaDoc x)
266       {
267          logger.error("Unexpected exception", x);
268          throw new IOException JavaDoc(x.toString());
269       }
270    }
271
272    private Logger getLogger()
273    {
274       return Log.getLogger(getClass().getName());
275    }
276 }
277
Popular Tags