From commits-return-31897-apmail-karaf-commits-archive=karaf.apache.org@karaf.apache.org Tue Sep 5 08:39:48 2017 Return-Path: X-Original-To: apmail-karaf-commits-archive@minotaur.apache.org Delivered-To: apmail-karaf-commits-archive@minotaur.apache.org Received: from mail.apache.org (hermes.apache.org [140.211.11.3]) by minotaur.apache.org (Postfix) with SMTP id 29C3C1A63C for ; Tue, 5 Sep 2017 08:39:48 +0000 (UTC) Received: (qmail 37375 invoked by uid 500); 5 Sep 2017 08:39:48 -0000 Delivered-To: apmail-karaf-commits-archive@karaf.apache.org Received: (qmail 37343 invoked by uid 500); 5 Sep 2017 08:39:48 -0000 Mailing-List: contact commits-help@karaf.apache.org; run by ezmlm Precedence: bulk List-Help: List-Unsubscribe: List-Post: List-Id: Reply-To: dev@karaf.apache.org Delivered-To: mailing list commits@karaf.apache.org Received: (qmail 37334 invoked by uid 99); 5 Sep 2017 08:39:47 -0000 Received: from git1-us-west.apache.org (HELO git1-us-west.apache.org) (140.211.11.23) by apache.org (qpsmtpd/0.29) with ESMTP; Tue, 05 Sep 2017 08:39:47 +0000 Received: by git1-us-west.apache.org (ASF Mail Server at git1-us-west.apache.org, from userid 33) id A9C9CE061C; Tue, 5 Sep 2017 08:39:47 +0000 (UTC) Content-Type: text/plain; charset="us-ascii" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit From: gnodet@apache.org To: commits@karaf.apache.org Message-Id: X-Mailer: ASF-Git Admin Mailer Subject: karaf git commit: [KARAF-5338] Unable to access the local JMX server on OSX Date: Tue, 5 Sep 2017 08:39:47 +0000 (UTC) Repository: karaf Updated Branches: refs/heads/karaf-4.1.x 94f550bd4 -> e7ec18362 [KARAF-5338] Unable to access the local JMX server on OSX Project: http://git-wip-us.apache.org/repos/asf/karaf/repo Commit: http://git-wip-us.apache.org/repos/asf/karaf/commit/e7ec1836 Tree: http://git-wip-us.apache.org/repos/asf/karaf/tree/e7ec1836 Diff: http://git-wip-us.apache.org/repos/asf/karaf/diff/e7ec1836 Branch: refs/heads/karaf-4.1.x Commit: e7ec18362fb1dd8e6836e0f6105541a5cb3afdc3 Parents: 94f550b Author: Guillaume Nodet Authored: Tue Sep 5 09:22:58 2017 +0200 Committer: Guillaume Nodet Committed: Tue Sep 5 10:39:39 2017 +0200 ---------------------------------------------------------------------- .../management/ConnectorServerFactory.java | 341 ++++++++++++++++++- 1 file changed, 327 insertions(+), 14 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/karaf/blob/e7ec1836/management/server/src/main/java/org/apache/karaf/management/ConnectorServerFactory.java ---------------------------------------------------------------------- diff --git a/management/server/src/main/java/org/apache/karaf/management/ConnectorServerFactory.java b/management/server/src/main/java/org/apache/karaf/management/ConnectorServerFactory.java index d0a20f0..d7ed04f 100644 --- a/management/server/src/main/java/org/apache/karaf/management/ConnectorServerFactory.java +++ b/management/server/src/main/java/org/apache/karaf/management/ConnectorServerFactory.java @@ -19,14 +19,22 @@ package org.apache.karaf.management; import org.apache.karaf.jaas.config.KeystoreManager; import org.apache.karaf.management.internal.MBeanInvocationHandler; +import java.io.Closeable; import java.io.IOException; import java.lang.reflect.Proxy; import java.net.BindException; import java.net.InetAddress; +import java.net.NetworkInterface; import java.net.ServerSocket; +import java.net.Socket; +import java.net.SocketAddress; +import java.net.SocketException; +import java.net.SocketImplFactory; +import java.nio.channels.ServerSocketChannel; import java.rmi.server.RMIClientSocketFactory; import java.rmi.server.RMIServerSocketFactory; import java.security.GeneralSecurityException; +import java.util.Enumeration; import java.util.Map; import javax.management.JMException; @@ -38,6 +46,7 @@ import javax.management.remote.JMXServiceURL; import javax.management.remote.rmi.RMIConnectorServer; import javax.net.ServerSocketFactory; import javax.net.ssl.KeyManagerFactory; +import javax.net.ssl.SSLParameters; import javax.net.ssl.SSLServerSocket; import javax.net.ssl.SSLServerSocketFactory; import javax.rmi.ssl.SslRMIClientSocketFactory; @@ -50,7 +59,7 @@ public class ConnectorServerFactory { private KarafMBeanServerGuard guard; private String serviceUrl; private String rmiServerHost; - private Map environment; + private Map environment; private ObjectName objectName; private boolean threaded = false; private boolean daemon = false; @@ -98,11 +107,11 @@ public class ConnectorServerFactory { this.rmiServerHost = rmiServerHost; } - public Map getEnvironment() { + public Map getEnvironment() { return environment; } - public void setEnvironment(Map environment) { + public void setEnvironment(Map environment) { this.environment = environment; } @@ -229,13 +238,14 @@ public class ConnectorServerFactory { throw new IllegalArgumentException("server must be set"); } JMXServiceURL url = new JMXServiceURL(this.serviceUrl); - setupKarafRMIServerSocketFactory(); if ( isClientAuth() ) { this.secured = true; } if ( this.secured ) { - this.setupSsl(); + setupSsl(); + } else { + setupKarafRMIServerSocketFactory(); } if ( ! AuthenticatorType.PASSWORD.equals( this.authenticatorType ) ) { @@ -306,9 +316,8 @@ public class ConnectorServerFactory { } private void setupSsl() throws GeneralSecurityException { - SSLServerSocketFactory sssf = keystoreManager.createSSLServerFactory(null, secureProtocol, algorithm, keyStore, keyAlias, trustStore,keyStoreAvailabilityTimeout); - RMIServerSocketFactory rssf = new KarafSslRMIServerSocketFactory(sssf, this.isClientAuth(), getRmiServerHost()); + RMIServerSocketFactory rssf = new KarafSslRMIServerSocketFactory(sssf, isClientAuth(), getRmiServerHost()); RMIClientSocketFactory rcsf = new SslRMIClientSocketFactory(); environment.put(RMIConnectorServer.RMI_SERVER_SOCKET_FACTORY_ATTRIBUTE, rssf); environment.put(RMIConnectorServer.RMI_CLIENT_SOCKET_FACTORY_ATTRIBUTE, rcsf); @@ -317,8 +326,8 @@ public class ConnectorServerFactory { } private void setupKarafRMIServerSocketFactory() { - RMIServerSocketFactory rmiServerSocketFactory = new KarafRMIServerSocketFactory(getRmiServerHost()); - environment.put(RMIConnectorServer.RMI_SERVER_SOCKET_FACTORY_ATTRIBUTE, rmiServerSocketFactory); + RMIServerSocketFactory rssf = new KarafRMIServerSocketFactory(getRmiServerHost()); + environment.put(RMIConnectorServer.RMI_SERVER_SOCKET_FACTORY_ATTRIBUTE, rssf); } private static class KarafSslRMIServerSocketFactory implements RMIServerSocketFactory { @@ -333,9 +342,16 @@ public class ConnectorServerFactory { } public ServerSocket createServerSocket(int port) throws IOException { - SSLServerSocket ss = (SSLServerSocket) sssf.createServerSocket(port, 50, InetAddress.getByName(rmiServerHost)); - ss.setNeedClientAuth(clientAuth); - return ss; + InetAddress host = InetAddress.getByName(rmiServerHost); + if (host.isLoopbackAddress()) { + final SSLServerSocket ss = (SSLServerSocket) sssf.createServerSocket(port, 50); + ss.setNeedClientAuth(clientAuth); + return new LocalOnlySSLServerSocket(ss); + } else { + final SSLServerSocket ss = (SSLServerSocket) sssf.createServerSocket(port, 50, InetAddress.getByName(rmiServerHost)); + ss.setNeedClientAuth(clientAuth); + return ss; + } } } @@ -347,10 +363,307 @@ public class ConnectorServerFactory { } public ServerSocket createServerSocket(int port) throws IOException { - ServerSocket serverSocket = (ServerSocket) ServerSocketFactory.getDefault().createServerSocket(port, 50, InetAddress.getByName(rmiServerHost)); - return serverSocket; + InetAddress host = InetAddress.getByName(rmiServerHost); + if (host.isLoopbackAddress()) { + final ServerSocket ss = ServerSocketFactory.getDefault().createServerSocket(port, 50); + return new LocalOnlyServerSocket(ss); + } else { + final ServerSocket ss = ServerSocketFactory.getDefault().createServerSocket(port, 50, InetAddress.getByName(rmiServerHost)); + return ss; + } + } + } + + private static class LocalOnlyServerSocket extends ServerSocket { + + private final ServerSocket ss; + + public LocalOnlyServerSocket(ServerSocket ss) throws IOException { + this.ss = ss; + } + + @Override + public void bind(SocketAddress endpoint) throws IOException { + ss.bind(endpoint); + } + + @Override + public void bind(SocketAddress endpoint, int backlog) throws IOException { + ss.bind(endpoint, backlog); + } + + @Override + public InetAddress getInetAddress() { + return ss.getInetAddress(); + } + + @Override + public int getLocalPort() { + return ss.getLocalPort(); + } + + @Override + public SocketAddress getLocalSocketAddress() { + return ss.getLocalSocketAddress(); + } + + @Override + public Socket accept() throws IOException { + return checkLocal(ss.accept()); + } + + @Override + public void close() throws IOException { + ss.close(); + } + + @Override + public ServerSocketChannel getChannel() { + return ss.getChannel(); + } + + @Override + public boolean isBound() { + return ss.isBound(); + } + + @Override + public boolean isClosed() { + return ss.isClosed(); + } + + @Override + public void setSoTimeout(int timeout) throws SocketException { + ss.setSoTimeout(timeout); + } + + @Override + public int getSoTimeout() throws IOException { + return ss.getSoTimeout(); + } + + @Override + public void setReuseAddress(boolean on) throws SocketException { + ss.setReuseAddress(on); + } + + @Override + public boolean getReuseAddress() throws SocketException { + return ss.getReuseAddress(); + } + + @Override + public String toString() { + return ss.toString(); + } + + @Override + public void setReceiveBufferSize(int size) throws SocketException { + ss.setReceiveBufferSize(size); + } + + @Override + public int getReceiveBufferSize() throws SocketException { + return ss.getReceiveBufferSize(); + } + + @Override + public void setPerformancePreferences(int connectionTime, int latency, int bandwidth) { + ss.setPerformancePreferences(connectionTime, latency, bandwidth); + } + } + + private static class LocalOnlySSLServerSocket extends SSLServerSocket { + + private final SSLServerSocket ss; + + public LocalOnlySSLServerSocket(SSLServerSocket ss) throws IOException { + this.ss = ss; + } + + @Override + public void bind(SocketAddress endpoint) throws IOException { + ss.bind(endpoint); + } + + @Override + public void bind(SocketAddress endpoint, int backlog) throws IOException { + ss.bind(endpoint, backlog); + } + + @Override + public InetAddress getInetAddress() { + return ss.getInetAddress(); + } + + @Override + public int getLocalPort() { + return ss.getLocalPort(); + } + + @Override + public SocketAddress getLocalSocketAddress() { + return ss.getLocalSocketAddress(); + } + + @Override + public Socket accept() throws IOException { + return checkLocal(ss.accept()); + } + + @Override + public void close() throws IOException { + ss.close(); + } + + @Override + public ServerSocketChannel getChannel() { + return ss.getChannel(); + } + + @Override + public boolean isBound() { + return ss.isBound(); + } + + @Override + public boolean isClosed() { + return ss.isClosed(); + } + + @Override + public void setSoTimeout(int timeout) throws SocketException { + ss.setSoTimeout(timeout); + } + + @Override + public int getSoTimeout() throws IOException { + return ss.getSoTimeout(); + } + + @Override + public void setReuseAddress(boolean on) throws SocketException { + ss.setReuseAddress(on); + } + + @Override + public boolean getReuseAddress() throws SocketException { + return ss.getReuseAddress(); + } + + @Override + public String toString() { + return ss.toString(); + } + + @Override + public void setReceiveBufferSize(int size) throws SocketException { + ss.setReceiveBufferSize(size); + } + + @Override + public int getReceiveBufferSize() throws SocketException { + return ss.getReceiveBufferSize(); + } + + @Override + public void setPerformancePreferences(int connectionTime, int latency, int bandwidth) { + ss.setPerformancePreferences(connectionTime, latency, bandwidth); + } + public String[] getEnabledCipherSuites() { + return ss.getEnabledCipherSuites(); + } + + public void setEnabledCipherSuites(String[] strings) { + ss.setEnabledCipherSuites(strings); + } + + public String[] getSupportedCipherSuites() { + return ss.getSupportedCipherSuites(); + } + + public String[] getSupportedProtocols() { + return ss.getSupportedProtocols(); + } + + public String[] getEnabledProtocols() { + return ss.getEnabledProtocols(); + } + + public void setEnabledProtocols(String[] strings) { + ss.setEnabledProtocols(strings); + } + + public void setNeedClientAuth(boolean b) { + ss.setNeedClientAuth(b); + } + + public boolean getNeedClientAuth() { + return ss.getNeedClientAuth(); + } + + public void setWantClientAuth(boolean b) { + ss.setWantClientAuth(b); + } + + public boolean getWantClientAuth() { + return ss.getWantClientAuth(); + } + + public void setUseClientMode(boolean b) { + ss.setUseClientMode(b); + } + + public boolean getUseClientMode() { + return ss.getUseClientMode(); + } + + public void setEnableSessionCreation(boolean b) { + ss.setEnableSessionCreation(b); + } + + public boolean getEnableSessionCreation() { + return ss.getEnableSessionCreation(); + } + + public SSLParameters getSSLParameters() { + return ss.getSSLParameters(); + } + + public void setSSLParameters(SSLParameters sslParameters) { + ss.setSSLParameters(sslParameters); } } + private static Socket checkLocal(Socket socket) throws IOException { + InetAddress addr = socket.getInetAddress(); + if (addr != null) { + if (addr.isLoopbackAddress()) { + return socket; + } else { + try { + Enumeration nis = NetworkInterface.getNetworkInterfaces(); + while (nis.hasMoreElements()) { + NetworkInterface ni = nis.nextElement(); + Enumeration ads = ni.getInetAddresses(); + while (ads.hasMoreElements()) { + InetAddress ad = ads.nextElement(); + if (ad.equals(addr)) { + return socket; + } + } + } + } catch (SocketException e) { + // Ignore + } + } + } + try { + socket.close(); + } catch (Exception e) { + // Ignore + } + throw new IOException("Only connections from clients running on the host where the RMI remote objects have been exported are accepted."); + } }