2014-11-13 3 views
0

그래서 저는 sslServer와 sslClient를 가지고 있습니다. 인증서를 생성하여 keyStore에 저장하고 keyStore를 서버의 기본 디렉토리에 배치합니다. 그런 다음이 keyStore를 clients 디렉토리에 복사합니다. 안전 한가? 누군가 내 클라이언트의 복사본을 다운로드하고 인증서/keyStore를 가져 와서 중간 공격에서 사람을 수행 할 수 없었습니까? 이 인증서 공유 문제를 어떻게 해결할 수 있습니까? 그것은 여기에 도움이 몇 가지 코드 인 경우 :Java SSLSockets : 클라이언트와 서버에서 동일한 keyStore가 안전한가요?

서버 :

/*This is a hidden class*/ 
class Server implements Runnable{ 
public Server(){ 

} 
@Override 
public void run() { 
    DataInputStream stringGetter = null; 
    try{ 
    KeyStore ks = KeyStore.getInstance(KeyStore.getDefaultType()); 

    char[] password = "iamakeystore".toCharArray(); 
    ks.load(null, password); 

    System.setProperty("javax.net.ssl.keyStore", "keyStore.jks"); 
    System.setProperty("javax.net.ssl.keyStorePassword", "iamakeystore"); 
    // Store away the keystore. 
    //FileOutputStream fos = new FileOutputStream("keyStore.jks"); 
    //ks.store(fos, password); 
    //fos.close(); 
    }catch(Exception e){ 

    } 
    SSLSocket sslsocket = null; 
    try { 
     SSLServerSocketFactory sslserversocketfactory = 
       (SSLServerSocketFactory) SSLServerSocketFactory.getDefault(); 
     SSLServerSocket sslserversocket = 
       (SSLServerSocket) sslserversocketfactory.createServerSocket(31030); 
     sslserversocket.setEnabledCipherSuites(sslserversocket.getSupportedCipherSuites()); 
     sslsocket = (SSLSocket) sslserversocket.accept(); 



     stringGetter= new DataInputStream(sslsocket.getInputStream()); 
     boolean done=false; 
     byte input=-1; 

     while(!done){ 

      input=stringGetter.readByte(); 

     switch(input){ 
      case 1:{ 

      } 
     } 
     } 
     sslsocket.close(); 
    } catch (IOException e) { 

     e.printStackTrace(); 
    }finally{ 
     if(stringGetter!=null){ 
      try { 
       stringGetter.close(); 
      } catch (IOException e) { 

       e.printStackTrace(); 
      } 
     } 
     if(sslsocket!=null){ 
      try { 
       sslsocket.close(); 
      } catch (IOException e) { 

       e.printStackTrace(); 
      } 
     } 

    } 

} 
} 

클라이언트 :

private void login(){ 
    System.setProperty("javax.net.ssl.keyStore", "keyStore.jks"); 
    System.setProperty("javax.net.ssl.keyStorePassword", "iamakeystore"); 
    SSLSocketFactory ssf = (SSLSocketFactory) SSLSocketFactory.getDefault(); 
    SSLSocket s = null; 
    DataOutputStream stringSender = null; 

    try { 
     s=(SSLSocket) ssf.createSocket("127.0.0.1", 31030); 
     s.setEnabledCipherSuites(s.getSupportedCipherSuites()); 
     s.startHandshake(); 
     stringSender= new DataOutputStream(s.getOutputStream()); 
     try { 
      Thread.sleep(500); 
     } catch (InterruptedException e) { 
      // TODO Auto-generated catch block 
      e.printStackTrace(); 
     } 
     stringSender.writeByte(1); 

     stringSender.flush(); 
    } catch (UnknownHostException e) { 
     // TODO Auto-generated catch block 
     e.printStackTrace(); 
    } catch (IOException e) { 
     // TODO Auto-generated catch block 
     e.printStackTrace(); 
    }finally{ 
     if(s!=null){ 
      try { 
       s.close(); 
      } catch (IOException e) { 
       // TODO Auto-generated catch block 
       e.printStackTrace(); 
      } 
     } 
    } 
} 
} 
+0

's.setEnabledCipherSuites (s.getSupportedCipherSuites())': 그렇게하지 마십시오. 안전하지 않기 때문에 기본적으로 사용하도록 설정되지 않은 것을 포함하여 지원되는 모든 암호화 제품군을 사용할 수 있습니다. – Bruno

+0

@ 브루노 어떤 대안이 있습니까? 대신 무엇을 사용할 수 있습니까? 협조 해 주셔서 감사합니다. 자습서 나 다른 것을 가르쳐 주시겠습니까? –

+1

기본적으로 사용하도록 설정된 암호를 사용합니다 (즉, 사용 가능한 암호화 제품군을 변경하지 않음). 사용 가능 또는 사용 불가능으로 설정하려는 암호 스위트를 알고있는 경우에만 사용 가능한 암호 세트를 변경해야합니다. – Bruno

답변

2

다음이 keyStore를 clients 디렉토리에 복사하십시오.

하지 마십시오.

안전한가요?

아니요. 안전하지 않고 무의미합니다. 키 저장소에는 개인 키가 들어 있습니다. 그러므로 키의 소유자에게는 사적인 것이어야합니다. 즉, 두 명의 키 소유자 (클라이언트 및 서버)는 각각 자체 키톱을 가져야합니다. 비공개가 아닌 개인 키는 자신의 목적에 위배되며 PKI와 TLS와 같은 모든 보안 문제에 완전히 의존합니다.

누군가 내 클라이언트 사본을 다운로드하고 인증서/keyStore를 받고 중간 공격자를 수행 할 수 없습니까?

예.

이 인증서 공유 문제를 어떻게 해결할 수 있습니까?

공유하지 마세요. 두 개의 키 저장소, 두 개의 키 쌍, 두 개의 인증서를 생성하고 서버와 클라이언트에서 각각 하나씩 사용하십시오. 그것들을 섞지 말고, 혼동하지 말고, 서로 섞지 마십시오.

+1

또한이 예제에서는 client-cert 인증이 사용되지 않으므로 하나의 키 쌍 및 인증서 만 생성해야합니다. 서버 키 저장소에서 해당 인증서를 내보내고 클라이언트에 제공하는 트러스트 스토어로 가져와야합니다. – Bruno

1

CA에서 서명이 인증서를 만들고 서로가 신뢰로이 보관하고있는 개인 키를 저장 이 방식으로 해당 사이드 키 스토어를 사용하면 상호 인증을 획득하고 중간 공격에서 사람을 방어 할 수 있습니다.

관련 문제