Ensure we support ALPN when using java 8u251 (#10196)

Motivation:

ALPN support was backported to java 8 lately. Ensure we support it if the user uses the latest java 8 release

Modifications:

- Update logic to be able to detect if ALPN is supported out of the box when using Java8
- Update jetty alpn version

Result:

Be able to use ALPN out of the box when using java 8u251
This commit is contained in:
Norman Maurer 2020-04-21 15:01:59 +02:00 committed by GitHub
parent 232c669fa4
commit 5cd00d22d9
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
7 changed files with 44 additions and 39 deletions

View File

@ -16,7 +16,6 @@
package io.netty.handler.ssl;
import io.netty.buffer.ByteBufAllocator;
import io.netty.util.internal.PlatformDependent;
import javax.net.ssl.SSLEngine;
@ -28,7 +27,7 @@ import javax.net.ssl.SSLEngine;
@Deprecated
public final class JdkAlpnApplicationProtocolNegotiator extends JdkBaseApplicationProtocolNegotiator {
private static final boolean AVAILABLE = Conscrypt.isAvailable() ||
jdkAlpnSupported() ||
JdkAlpnSslUtils.supportsAlpn() ||
JettyAlpnSslEngine.isAvailable();
private static final SslEngineWrapperFactory ALPN_WRAPPER = AVAILABLE ? new AlpnWrapper() : new FailureWrapper();
@ -134,8 +133,12 @@ public final class JdkAlpnApplicationProtocolNegotiator extends JdkBaseApplicati
return isServer ? ConscryptAlpnSslEngine.newServerEngine(engine, alloc, applicationNegotiator)
: ConscryptAlpnSslEngine.newClientEngine(engine, alloc, applicationNegotiator);
}
if (jdkAlpnSupported()) {
return new Java9SslEngine(engine, applicationNegotiator, isServer);
// ALPN support was recently backported to Java8 as
// https://bugs.java.com/bugdatabase/view_bug.do?bug_id=8230977.
// Because of this lets not do a Java version runtime check but just depend on if the required methods are
// present
if (JdkAlpnSslUtils.supportsAlpn()) {
return new JdkAlpnSslEngine(engine, applicationNegotiator, isServer);
}
if (JettyAlpnSslEngine.isAvailable()) {
return isServer ? JettyAlpnSslEngine.newServerEngine(engine, applicationNegotiator)
@ -145,10 +148,6 @@ public final class JdkAlpnApplicationProtocolNegotiator extends JdkBaseApplicati
}
}
static boolean jdkAlpnSupported() {
return PlatformDependent.javaVersion() >= 9 && Java9SslUtils.supportsAlpn();
}
static boolean isAlpnSupported() {
return AVAILABLE;
}

View File

@ -32,7 +32,7 @@ import static io.netty.handler.ssl.JdkApplicationProtocolNegotiator.ProtocolSele
import static io.netty.handler.ssl.JdkApplicationProtocolNegotiator.ProtocolSelector;
@SuppressJava6Requirement(reason = "Usage guarded by java version check")
final class Java9SslEngine extends JdkSslEngine {
final class JdkAlpnSslEngine extends JdkSslEngine {
private final ProtocolSelectionListener selectionListener;
private final AlpnSelector alpnSelector;
@ -79,18 +79,20 @@ final class Java9SslEngine extends JdkSslEngine {
}
}
Java9SslEngine(SSLEngine engine, JdkApplicationProtocolNegotiator applicationNegotiator, boolean isServer) {
JdkAlpnSslEngine(SSLEngine engine,
@SuppressWarnings("deprecation") JdkApplicationProtocolNegotiator applicationNegotiator,
boolean isServer) {
super(engine);
if (isServer) {
selectionListener = null;
alpnSelector = new AlpnSelector(applicationNegotiator.protocolSelectorFactory().
newSelector(this, new LinkedHashSet<String>(applicationNegotiator.protocols())));
Java9SslUtils.setHandshakeApplicationProtocolSelector(engine, alpnSelector);
JdkAlpnSslUtils.setHandshakeApplicationProtocolSelector(engine, alpnSelector);
} else {
selectionListener = applicationNegotiator.protocolListenerFactory()
.newListener(this, applicationNegotiator.protocols());
alpnSelector = null;
Java9SslUtils.setApplicationProtocols(engine, applicationNegotiator.protocols());
JdkAlpnSslUtils.setApplicationProtocols(engine, applicationNegotiator.protocols());
}
}
@ -153,7 +155,7 @@ final class Java9SslEngine extends JdkSslEngine {
@Override
void setNegotiatedApplicationProtocol(String applicationProtocol) {
// Do nothing as this is handled internally by the Java9 implementation of SSLEngine.
// Do nothing as this is handled internally by the Java8u251+ implementation of SSLEngine.
}
@Override
@ -162,24 +164,24 @@ final class Java9SslEngine extends JdkSslEngine {
if (protocol != null) {
return protocol.isEmpty() ? null : protocol;
}
return protocol;
return null;
}
// These methods will override the methods defined by Java 9. As we compile with Java8 we can not add
// @Override annotations here.
// These methods will override the methods defined by Java 8u251 and later. As we may compile with an earlier
// java8 version we don't use @Override annotations here.
public String getApplicationProtocol() {
return Java9SslUtils.getApplicationProtocol(getWrappedEngine());
return JdkAlpnSslUtils.getApplicationProtocol(getWrappedEngine());
}
public String getHandshakeApplicationProtocol() {
return Java9SslUtils.getHandshakeApplicationProtocol(getWrappedEngine());
return JdkAlpnSslUtils.getHandshakeApplicationProtocol(getWrappedEngine());
}
public void setHandshakeApplicationProtocolSelector(BiFunction<SSLEngine, List<String>, String> selector) {
Java9SslUtils.setHandshakeApplicationProtocolSelector(getWrappedEngine(), selector);
JdkAlpnSslUtils.setHandshakeApplicationProtocolSelector(getWrappedEngine(), selector);
}
public BiFunction<SSLEngine, List<String>, String> getHandshakeApplicationProtocolSelector() {
return Java9SslUtils.getHandshakeApplicationProtocolSelector(getWrappedEngine());
return JdkAlpnSslUtils.getHandshakeApplicationProtocolSelector(getWrappedEngine());
}
}

View File

@ -32,8 +32,8 @@ import io.netty.util.internal.logging.InternalLogger;
import io.netty.util.internal.logging.InternalLoggerFactory;
@SuppressJava6Requirement(reason = "Usage guarded by java version check")
final class Java9SslUtils {
private static final InternalLogger logger = InternalLoggerFactory.getInstance(Java9SslUtils.class);
final class JdkAlpnSslUtils {
private static final InternalLogger logger = InternalLoggerFactory.getInstance(JdkAlpnSslUtils.class);
private static final Method SET_APPLICATION_PROTOCOLS;
private static final Method GET_APPLICATION_PROTOCOL;
private static final Method GET_HANDSHAKE_APPLICATION_PROTOCOL;
@ -41,11 +41,11 @@ final class Java9SslUtils {
private static final Method GET_HANDSHAKE_APPLICATION_PROTOCOL_SELECTOR;
static {
Method getHandshakeApplicationProtocol = null;
Method getApplicationProtocol = null;
Method setApplicationProtocols = null;
Method setHandshakeApplicationProtocolSelector = null;
Method getHandshakeApplicationProtocolSelector = null;
Method getHandshakeApplicationProtocol;
Method getApplicationProtocol;
Method setApplicationProtocols;
Method setHandshakeApplicationProtocolSelector;
Method getHandshakeApplicationProtocolSelector;
try {
SSLContext context = SSLContext.getInstance(JdkSslContext.PROTOCOL);
@ -97,8 +97,11 @@ final class Java9SslUtils {
});
getHandshakeApplicationProtocolSelector.invoke(engine);
} catch (Throwable t) {
logger.error("Unable to initialize Java9SslUtils, but the detected javaVersion was: {}",
PlatformDependent.javaVersion(), t);
int version = PlatformDependent.javaVersion();
if (version >= 9) {
// We only log when run on java9+ as this is expected on some earlier java8 versions
logger.error("Unable to initialize JdkAlpnSslUtils, but the detected java version was: {}", version, t);
}
getHandshakeApplicationProtocol = null;
getApplicationProtocol = null;
setApplicationProtocols = null;
@ -112,7 +115,7 @@ final class Java9SslUtils {
GET_HANDSHAKE_APPLICATION_PROTOCOL_SELECTOR = getHandshakeApplicationProtocolSelector;
}
private Java9SslUtils() {
private JdkAlpnSslUtils() {
}
static boolean supportsAlpn() {
@ -164,6 +167,7 @@ final class Java9SslUtils {
}
}
@SuppressWarnings("unchecked")
static BiFunction<SSLEngine, List<String>, String> getHandshakeApplicationProtocolSelector(SSLEngine engine) {
try {
return (BiFunction<SSLEngine, List<String>, String>)

View File

@ -79,10 +79,10 @@ public class JdkSslEngineTest extends SSLEngineTest {
return null;
}
},
ALPN_JAVA9 {
ALPN_JAVA {
@Override
boolean isAvailable() {
return PlatformDependent.javaVersion() >= 9 && Java9SslUtils.supportsAlpn();
return JdkAlpnSslUtils.supportsAlpn();
}
@Override

View File

@ -339,7 +339,7 @@ final class OpenSslErrorStackAssertSSLEngine extends JdkSslEngine implements Ref
public String getApplicationProtocol() {
if (PlatformDependent.javaVersion() >= 9) {
try {
return Java9SslUtils.getApplicationProtocol(getWrappedEngine());
return JdkAlpnSslUtils.getApplicationProtocol(getWrappedEngine());
} finally {
assertErrorStackEmpty();
}
@ -350,7 +350,7 @@ final class OpenSslErrorStackAssertSSLEngine extends JdkSslEngine implements Ref
public String getHandshakeApplicationProtocol() {
if (PlatformDependent.javaVersion() >= 9) {
try {
return Java9SslUtils.getHandshakeApplicationProtocol(getWrappedEngine());
return JdkAlpnSslUtils.getHandshakeApplicationProtocol(getWrappedEngine());
} finally {
assertErrorStackEmpty();
}
@ -361,7 +361,7 @@ final class OpenSslErrorStackAssertSSLEngine extends JdkSslEngine implements Ref
public void setHandshakeApplicationProtocolSelector(BiFunction<SSLEngine, List<String>, String> selector) {
if (PlatformDependent.javaVersion() >= 9) {
try {
Java9SslUtils.setHandshakeApplicationProtocolSelector(getWrappedEngine(), selector);
JdkAlpnSslUtils.setHandshakeApplicationProtocolSelector(getWrappedEngine(), selector);
} finally {
assertErrorStackEmpty();
}
@ -372,7 +372,7 @@ final class OpenSslErrorStackAssertSSLEngine extends JdkSslEngine implements Ref
public BiFunction<SSLEngine, List<String>, String> getHandshakeApplicationProtocolSelector() {
if (PlatformDependent.javaVersion() >= 9) {
try {
return Java9SslUtils.getHandshakeApplicationProtocolSelector(getWrappedEngine());
return JdkAlpnSslUtils.getHandshakeApplicationProtocolSelector(getWrappedEngine());
} finally {
assertErrorStackEmpty();
}

View File

@ -1157,9 +1157,9 @@ public abstract class SSLEngineTest {
assertEquals(expectedApplicationProtocol, appProto);
SSLEngine engine = handler.engine();
if (engine instanceof Java9SslEngine) {
if (engine instanceof JdkAlpnSslEngine) {
// Also verify the Java9 exposed method.
Java9SslEngine java9SslEngine = (Java9SslEngine) engine;
JdkAlpnSslEngine java9SslEngine = (JdkAlpnSslEngine) engine;
assertEquals(expectedApplicationProtocol == null ? StringUtil.EMPTY_STRING : expectedApplicationProtocol,
java9SslEngine.getApplicationProtocol());
}

View File

@ -314,7 +314,7 @@
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
<netty.build.version>26</netty.build.version>
<jboss.marshalling.version>1.4.11.Final</jboss.marshalling.version>
<jetty.alpnAgent.version>2.0.8</jetty.alpnAgent.version>
<jetty.alpnAgent.version>2.0.10</jetty.alpnAgent.version>
<jetty.alpnAgent.path>"${settings.localRepository}"/org/mortbay/jetty/alpn/jetty-alpn-agent/${jetty.alpnAgent.version}/jetty-alpn-agent-${jetty.alpnAgent.version}.jar</jetty.alpnAgent.path>
<argLine.common>
-server