#java #ssl #server #ssl-certificate #client
#java #ssl #сервер #ssl-сертификат #клиент
Вопрос:
Здравствуйте, я пытаюсь запустить сервер SSL и клиентскую программу. Сначала я создаю сертификат с помощью команды cmd «keytool -genkey -keystore mySrvKeyStore -keyalg RSA». 123456 — это пароль после ввода информации. Я помещаю сертификат в ту же папку, что и сервер и клиент, запускаю сервер и получаю следующую ошибку: «java.lang.Исключение IllegalStateException: SSLContext не инициализирован »
Сервер:
public class SSLServer {
private static int port = 4000;
private static SSLServerSocketFactory sf;
private static SSLServerSocket ss;
public static void StabilireConexiune(int nrPort) {
try {
sf = (SSLServerSocketFactory) SSLServer.getServerSocketFactory();
ss = (SSLServerSocket) sf.createServerSocket(nrPort);
System.out.println("Server connected ready to accept new connections at the address " ss.getLocalPort());
String[] enable = {"TLS_DH_anon_WITH_AES_128_CBC_SHA"};
ss.setEnabledCipherSuites(enable);
String[] cipherSuites = ss.getEnabledCipherSuites();
System.out.println("CipherSuites: ");
for (int i = 0; i < cipherSuites.length; i ) {
System.out.println(cipherSuites[i]);
}
} catch (Exception ex) {
ex.printStackTrace();
}
}
private static SSLSocket clientSocket;
public static void ConectareClient(){
try{
clientSocket = (SSLSocket) ss.accept();
System.out.println("Client connected succesfully");
InputStream input = clientSocket.getInputStream();
InputStreamReader inputreader = new InputStreamReader(input);
BufferedReader br = new BufferedReader(inputreader);
String string = null;
while( (string = br.readLine()) != null){
System.out.println(string);
System.out.flush();
}
}catch(Exception ex){
ex.printStackTrace();
}
finally{
try{
clientSocket.close();
}catch(IOException ex){
ex.printStackTrace();
}
}
}
private static ServerSocketFactory getServerSocketFactory() throws NoSuchAlgorithmException{
SSLServerSocketFactory ssf = null;
try{
KeyManagerFactory kmf;
KeyStore ks;
SSLContext ctx;
char[] passphrase = "123456".toCharArray();
ctx = SSLContext.getInstance("TLS");
kmf = KeyManagerFactory.getInstance("SunX509");
ks = KeyStore.getInstance("JKS");
ks.load(new FileInputStream("mySrvKeystore"), passphrase);
kmf.init(ks, passphrase);
ctx.getServerSocketFactory();
return ssf;
}catch(Exception ex){
ex.printStackTrace();
}
return null;
}
public static void main(String args[]){
if(args.length != 0){
port = Integer.parseInt(args[0]);
}
StabilireConexiune(port);
while(true){
ConectareClient();
}
}}
Клиент:
public class SSLClient {
public static void main(String args[]) {
conectare("127.0.0.1", 4000);
}
private static SSLSocket socket;
public static void conectare(String host, int port) {
try {
SSLSocketFactory factory = (SSLSocketFactory) SSLClient.getSocketFactory();
socket = (SSLSocket) factory.createSocket(host, port);
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
String[] enable = {"TLS_DH_anon_WITH_AES_128_CBC_SHA"};
socket.setEnabledCipherSuites(enable);
String[] cipherSuites = socket.getEnabledCipherSuites();
for (int i = 0; i < cipherSuites.length; i ) {
System.out.println(cipherSuites[i]);
}
socket.addHandshakeCompletedListener(new HandshakeCompletedListener() {
public void handshakeCompleted(HandshakeCompletedEvent event) {
System.out.println("handshake done");
}
});
socket.startHandshake();
PrintWriter out = new PrintWriter(new BufferedWriter(new OutputStreamWriter(socket.getOutputStream())));
System.out.println("Give a message to the server...");
String string = br.readLine();
out.println("Message to the server..." string);
out.println();
out.flush();
}catch(IOException ex){
ex.printStackTrace();
}
finally{
try{
socket.close();
}catch(IOException ex){
ex.printStackTrace();
}
}
}
private static SocketFactory getSocketFactory(){
SSLSocketFactory ssf = null;
try{
SSLContext ctx;
KeyManagerFactory kmf;
KeyStore ks;
char[] passphrase = "123456".toCharArray();
ctx = SSLContext.getInstance("TLS");
kmf = KeyManagerFactory.getInstance("SunX509");
ks = KeyStore.getInstance("JKS");
ks.load(new FileInputStream("mySrvKeystore"), passphrase);
kmf.init(ks, passphrase);
ctx.init(kmf.getKeyManagers(), null, null);
ssf = ctx.getSocketFactory();
return ssf;
}catch(Exception e){
e.printStackTrace();
}
return null;
}}
Пожалуйста, помогите мне, в чем проблема?
Ответ №1:
Ошибка в этих двух строках:
SSLContext ctx = SSLContext.getInstance("TLS");
ctx.getServerSocketFactory();
Почему он выдает это исключение? Метод getServerSocketFactory() утверждает:
Выдает: исключение IllegalStateException — если SSLContextImpl требует инициализации, а init() не был вызван
В клиенте вы действительно вызываете ctx.init(kmf.getKeyManagers(), null, null);
перед вызовом ctx.getServerSocketFactory();
Но на сервере вы не вызываете это — вы только инициализируете KeyManagerFactory.
Комментарии:
1. Большое вам спасибо. Я добавил строку, и теперь она работает.