2016-06-09 69 views
10

我想要在android設備上有一個SSL加密的TCP服務器,並且要連接到設備的計算機上有一個客戶端。當Android設備處於wifi狀態時,SSLSocket掛在getInputStream中

我使用自己的密鑰庫在Android設備上創建SSLServerSocket。

final KeyStore localTrustStore = KeyStore.getInstance("BKS"); //NON-NLS 
final InputStream in = context.getResources().openRawResource(R.raw.syncapp); 
localTrustStore.load(in, "secret".toCharArray()); //Keystore pw 
in.close(); 

final SSLContext sslContext = SSLContext.getInstance("TLSv1.2"); //NON-NLS 

final TrustManagerFactory trustManagerFactory = TrustManagerFactory.getInstance(KeyManagerFactory.getDefaultAlgorithm()); 
trustManagerFactory.init(localTrustStore); 

final KeyManagerFactory keyManagerFactory = KeyManagerFactory.getInstance(KeyManagerFactory.getDefaultAlgorithm()); 
keyManagerFactory.init(localTrustStore, "secret".toCharArray()); //privat key pw 

sslContext.init(keyManagerFactory.getKeyManagers(), trustManagerFactory.getTrustManagers(), null); 

serverSocket = sslContext.getServerSocketFactory().createServerSocket(SERVER_PORT); 
((SSLServerSocket) serverSocket).setNeedClientAuth(true); 

然後我等待客戶端連接。當客戶端需要連接一個新的線程啓動,並得到流要求:

final DataInputStream input = new DataInputStream(this.clientSocket.getInputStream()); 
final DataOutputStream output = new DataOutputStream(new BufferedOutputStream(clientSocket.getOutputStream())); 

首先我用這個代碼與USB-圈養獲得計算機和Android設備之間的連接。所以沒有啓用Wifi /網絡。一切都很完美。

然後我激活了android設備上的wifi,並連接到沒有互聯網的wlan。 但現在調用getInputStream()似乎需要5到10秒。 如果我停用SSL,它可以很好地工作。 如果WLAN連接到互聯網,那麼也不會有延遲。 我用Android 4.2和5.1測試了這個。 更新:現在我可以用Android 6測試這個問題。而且這個問題似乎在那裏得到修復...

握手完成正確,但之後似乎在Android設備上有某種延遲。 (對getInputStream的調用會消耗這段時間) 有些開發人員說它將執行DNS反向查找,這將會超時。

enter image description here

看看捕獲,而無線網絡被禁用作出的第一個連接。數據傳輸耗時0.3秒。然後我只是激活了無線網絡,我沒有通過無線連接,它仍然通過USB通信。它花了5秒。

我在這裏也發現了這個問題,但他們使用的是客戶端套接字。我需要一個服務器套接字。有沒有人有任何想法如何解決這個問題?

TLS connection using SSLSocket is slow in Android OS

+0

它沒有任何意義,使用相同的文件既密鑰存儲和信任存儲。 – EJP

+0

你能詳細說明一下嗎?我有一個密鑰庫的服務器與密鑰對和客戶端的公鑰。客戶端有自己的密鑰對和服務器的公鑰。所以他們可以相互驗證,但沒有人可以與它聯繫。 – Rocket

+0

信任商店是您信任的人。這是可能由委員會決定的事情,可能是整個網站或整個公司範圍,或者實際上是JDK範圍的默認情況。密鑰庫包含您自己的私鑰和簽名證書。這些是**祕密**。他們周圍的安全制度在每種情況下都完全不同。它沒有任何意義使用相同的物理文件。 – EJP

回答

0

你是正確的,有是超時反向DNS查找。在某些Java運行時環境中,在與原始IP地址握手期間,SSLContext會不必要地執行查找服務器的IP地址。這是爲了確定服務器證書的通用名稱是否匹配。嘗試使用這裏提到的解決方案之一:

How to disable Java's SSL Reverse DNS Lookup

相關問題