--- old/src/java.base/share/classes/sun/security/ssl/MaxFragmentLengthExtension.java 2018-05-11 15:09:32.264014700 -0700 +++ /dev/null 2018-05-11 10:42:23.849000000 -0700 @@ -1,139 +0,0 @@ -/* - * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved. - * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. - * - * This code is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License version 2 only, as - * published by the Free Software Foundation. Oracle designates this - * particular file as subject to the "Classpath" exception as provided - * by Oracle in the LICENSE file that accompanied this code. - * - * This code is distributed in the hope that it will be useful, but WITHOUT - * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - * version 2 for more details (a copy is included in the LICENSE file that - * accompanied this code). - * - * You should have received a copy of the GNU General Public License version - * 2 along with this work; if not, write to the Free Software Foundation, - * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. - * - * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA - * or visit www.oracle.com if you need additional information or have any - * questions. - */ - -package sun.security.ssl; - -import java.io.IOException; -import javax.net.ssl.SSLProtocolException; - -/* - * [RFC6066] TLS specifies a fixed maximum plaintext fragment length of - * 2^14 bytes. It may be desirable for constrained clients to negotiate - * a smaller maximum fragment length due to memory limitations or bandwidth - * limitations. - * - * In order to negotiate smaller maximum fragment lengths, clients MAY - * include an extension of type "max_fragment_length" in the (extended) - * client hello. The "extension_data" field of this extension SHALL - * contain: - * - * enum{ - * 2^9(1), 2^10(2), 2^11(3), 2^12(4), (255) - * } MaxFragmentLength; - * - * whose value is the desired maximum fragment length. - */ -final class MaxFragmentLengthExtension extends HelloExtension { - - private static final int MAX_FRAGMENT_LENGTH_512 = 1; // 2^9 - private static final int MAX_FRAGMENT_LENGTH_1024 = 2; // 2^10 - private static final int MAX_FRAGMENT_LENGTH_2048 = 3; // 2^11 - private static final int MAX_FRAGMENT_LENGTH_4096 = 4; // 2^12 - - final int maxFragmentLength; - - MaxFragmentLengthExtension(int fragmentSize) { - super(ExtensionType.EXT_MAX_FRAGMENT_LENGTH); - - if (fragmentSize < 1024) { - maxFragmentLength = MAX_FRAGMENT_LENGTH_512; - } else if (fragmentSize < 2048) { - maxFragmentLength = MAX_FRAGMENT_LENGTH_1024; - } else if (fragmentSize < 4096) { - maxFragmentLength = MAX_FRAGMENT_LENGTH_2048; - } else { - maxFragmentLength = MAX_FRAGMENT_LENGTH_4096; - } - } - - MaxFragmentLengthExtension(HandshakeInStream s, int len) - throws IOException { - super(ExtensionType.EXT_MAX_FRAGMENT_LENGTH); - - // check the extension length - if (len != 1) { - throw new SSLProtocolException("Invalid " + type + " extension"); - } - - maxFragmentLength = s.getInt8(); - if ((maxFragmentLength > 4) || (maxFragmentLength < 1)) { - throw new SSLProtocolException("Invalid " + type + " extension"); - } - } - - // Length of the encoded extension, including the type and length fields - @Override - int length() { - return 5; // 4: extension type and length fields - // 1: MaxFragmentLength field - } - - @Override - void send(HandshakeOutStream s) throws IOException { - s.putInt16(type.id); - s.putInt16(1); - s.putInt8(maxFragmentLength); - } - - int getMaxFragLen() { - switch (maxFragmentLength) { - case MAX_FRAGMENT_LENGTH_512: - return 512; - case MAX_FRAGMENT_LENGTH_1024: - return 1024; - case MAX_FRAGMENT_LENGTH_2048: - return 2048; - case MAX_FRAGMENT_LENGTH_4096: - return 4096; - } - - // unlikely to happen - return -1; - } - - static boolean needFragLenNego(int fragmentSize) { - return (fragmentSize > 0) && (fragmentSize <= 4096); - } - - static int getValidMaxFragLen(int fragmentSize) { - if (fragmentSize < 1024) { - return 512; - } else if (fragmentSize < 2048) { - return 1024; - } else if (fragmentSize < 4096) { - return 2048; - } else if (fragmentSize == 4096) { - return 4096; - } else { - return 16384; - } - } - - @Override - public String toString() { - return "Extension " + type + ", max_fragment_length: " + - "(2^" + (maxFragmentLength + 8) + ")"; - } -} --- /dev/null 2018-05-11 10:42:23.849000000 -0700 +++ new/src/java.base/share/classes/sun/security/ssl/MaxFragExtension.java 2018-05-11 15:09:31.521298900 -0700 @@ -0,0 +1,620 @@ +/* + * Copyright (c) 2015, 2018, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Oracle designates this + * particular file as subject to the "Classpath" exception as provided + * by Oracle in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ + +package sun.security.ssl; + +import java.io.IOException; +import java.nio.ByteBuffer; +import javax.net.ssl.SSLProtocolException; +import static sun.security.ssl.SSLExtension.CH_MAX_FRAGMENT_LENGTH; +import static sun.security.ssl.SSLExtension.EE_MAX_FRAGMENT_LENGTH; +import sun.security.ssl.SSLExtension.ExtensionConsumer; +import static sun.security.ssl.SSLExtension.SH_MAX_FRAGMENT_LENGTH; +import sun.security.ssl.SSLExtension.SSLExtensionSpec; +import sun.security.ssl.SSLHandshake.HandshakeMessage; + +/** + * Pack of the "max_fragment_length" extensions [RFC6066]. + */ +final class MaxFragExtension { + static final HandshakeProducer chNetworkProducer = + new CHMaxFragmentLengthProducer(); + static final ExtensionConsumer chOnLoadConcumer = + new CHMaxFragmentLengthConsumer(); + + static final HandshakeProducer shNetworkProducer = + new SHMaxFragmentLengthProducer(); + static final ExtensionConsumer shOnLoadConcumer = + new SHMaxFragmentLengthConsumer(); + static final HandshakeConsumer shOnTradeConsumer = + new SHMaxFragmentLengthUpdate(); + + static final HandshakeProducer eeNetworkProducer = + new EEMaxFragmentLengthProducer(); + static final ExtensionConsumer eeOnLoadConcumer = + new EEMaxFragmentLengthConsumer(); + static final HandshakeConsumer eeOnTradeConsumer = + new EEMaxFragmentLengthUpdate(); + + static final SSLStringize maxFragLenStringize = + new MaxFragLenStringize(); + + /** + * The "max_fragment_length" extension [RFC 6066]. + */ + static final class MaxFragLenSpec implements SSLExtensionSpec { + byte id; + + private MaxFragLenSpec(byte id) { + this.id = id; + } + + private MaxFragLenSpec(ByteBuffer buffer) throws IOException { + if (buffer.remaining() != 1) { + throw new SSLProtocolException( + "Invalid max_fragment_length extension data"); + } + + this.id = buffer.get(); + } + + @Override + public String toString() { + return MaxFragLenEnum.nameOf(id); + } + } + + private static final class MaxFragLenStringize implements SSLStringize { + @Override + public String toString(ByteBuffer buffer) { + try { + return (new MaxFragLenSpec(buffer)).toString(); + } catch (IOException ioe) { + // For debug logging only, so please swallow exceptions. + return ioe.getMessage(); + } + } + } + + static enum MaxFragLenEnum { + MFL_512 ((byte)0x01, 512, "2^9"), + MFL_1024 ((byte)0x02, 1024, "2^10"), + MFL_2048 ((byte)0x03, 2048, "2^11"), + MFL_4096 ((byte)0x04, 4096, "2^12"); + + final byte id; + final int fragmentSize; + final String description; + + private MaxFragLenEnum(byte id, int fragmentSize, String description) { + this.id = id; + this.fragmentSize = fragmentSize; + this.description = description; + } + + private static MaxFragLenEnum valueOf(byte id) { + for (MaxFragLenEnum mfl : MaxFragLenEnum.values()) { + if (mfl.id == id) { + return mfl; + } + } + + return null; + } + + private static String nameOf(byte id) { + for (MaxFragLenEnum mfl : MaxFragLenEnum.values()) { + if (mfl.id == id) { + return mfl.description; + } + } + + return "UNDEFINED-MAX-FRAGMENT-LENGTH(" + id + ")"; + } + + /** + * Returns the best match enum constant of the specified + * fragment size. + */ + static MaxFragLenEnum valueOf(int fragmentSize) { + if (fragmentSize <= 0) { + return null; + } else if (fragmentSize < 1024) { + return MFL_512; + } else if (fragmentSize < 2048) { + return MFL_1024; + } else if (fragmentSize < 4096) { + return MFL_2048; + } else if (fragmentSize == 4096) { + return MFL_4096; + } + + return null; + } + } + + /** + * Network data producer of a "max_fragment_length" extension in + * the ClientHello handshake message. + */ + private static final + class CHMaxFragmentLengthProducer implements HandshakeProducer { + // Prevent instantiation of this class. + private CHMaxFragmentLengthProducer() { + // blank + } + + @Override + public byte[] produce(ConnectionContext context, + HandshakeMessage message) throws IOException { + // The producing happens in client side only. + ClientHandshakeContext chc = (ClientHandshakeContext)context; + + // Is it a supported and enabled extension? + if (!chc.sslConfig.isAvailable(CH_MAX_FRAGMENT_LENGTH)) { + if (SSLLogger.isOn && SSLLogger.isOn("ssl,handshake")) { + SSLLogger.fine( + "Ignore unavailable max_fragment_length extension"); + } + return null; + } + + // Produce the extension and update the context. + int requestedMFLength; + if (chc.isResumption && (chc.resumingSession != null)) { + // The same extension should be sent for resumption. + requestedMFLength = + chc.resumingSession.getNegotiatedMaxFragSize(); + } else if (chc.sslConfig.maximumPacketSize != 0) { + // Maybe we can calculate the fragment size more accurate + // by condering the enabled cipher suites in the future. + requestedMFLength = chc.sslConfig.maximumPacketSize; + if (chc.sslContext.isDTLS()) { + requestedMFLength -= DTLSRecord.maxPlaintextPlusSize; + } else { + requestedMFLength -= SSLRecord.maxPlaintextPlusSize; + } + } else { + // Need no max_fragment_length extension. + requestedMFLength = -1; + } + + MaxFragLenEnum mfl = MaxFragLenEnum.valueOf(requestedMFLength); + if (mfl != null) { + // update the context. + chc.handshakeExtensions.put( + CH_MAX_FRAGMENT_LENGTH, new MaxFragLenSpec(mfl.id)); + + return new byte[] { mfl.id }; + } else { + // log and ignore, no MFL extension. + chc.maxFragmentLength = -1; + if (SSLLogger.isOn && SSLLogger.isOn("ssl,handshake")) { + SSLLogger.fine( + "No available max_fragment_length extension can " + + "be used for fragment size of " + + requestedMFLength + "bytes"); + } + } + + return null; + } + } + + /** + * Network data consumer of a "max_fragment_length" extension in + * the ClientHello handshake message. + */ + private static final + class CHMaxFragmentLengthConsumer implements ExtensionConsumer { + // Prevent instantiation of this class. + private CHMaxFragmentLengthConsumer() { + // blank + } + + @Override + public void consume(ConnectionContext context, + HandshakeMessage message, ByteBuffer buffer) throws IOException { + // The comsuming happens in server side only. + ServerHandshakeContext shc = (ServerHandshakeContext)context; + + if (!shc.sslConfig.isAvailable(CH_MAX_FRAGMENT_LENGTH)) { + if (SSLLogger.isOn && SSLLogger.isOn("ssl,handshake")) { + SSLLogger.fine( + "Ignore unavailable max_fragment_length extension"); + } + return; // ignore the extension + } + + // Parse the extension. + MaxFragLenSpec spec; + try { + spec = new MaxFragLenSpec(buffer); + } catch (IOException ioe) { + shc.conContext.fatal(Alert.UNEXPECTED_MESSAGE, ioe); + return; // fatal() always throws, make the compiler happy. + } + + MaxFragLenEnum mfle = MaxFragLenEnum.valueOf(spec.id); + if (mfle == null) { + shc.conContext.fatal(Alert.ILLEGAL_PARAMETER, + "the requested maximum fragment length is other " + + "than the allowed values"); + } + + // Update the context. + shc.maxFragmentLength = mfle.fragmentSize; + shc.handshakeExtensions.put(CH_MAX_FRAGMENT_LENGTH, spec); + + // No impact on session resumption. + } + } + + /** + * Network data producer of a "max_fragment_length" extension in + * the ServerHello handshake message. + */ + private static final + class SHMaxFragmentLengthProducer implements HandshakeProducer { + // Prevent instantiation of this class. + private SHMaxFragmentLengthProducer() { + // blank + } + + @Override + public byte[] produce(ConnectionContext context, + HandshakeMessage message) throws IOException { + // The producing happens in server side only. + ServerHandshakeContext shc = (ServerHandshakeContext)context; + + // In response to "max_fragment_length" extension request only + MaxFragLenSpec spec = (MaxFragLenSpec) + shc.handshakeExtensions.get(CH_MAX_FRAGMENT_LENGTH); + if (spec == null) { + if (SSLLogger.isOn && SSLLogger.isOn("ssl,handshake")) { + SSLLogger.finest( + "Ignore unavailable max_fragment_length extension"); + } + return null; // ignore the extension + } + + if ((shc.maxFragmentLength > 0) && + (shc.sslConfig.maximumPacketSize != 0)) { + int estimatedMaxFragSize = + shc.negotiatedCipherSuite.calculatePacketSize( + shc.maxFragmentLength, shc.negotiatedProtocol, + shc.sslContext.isDTLS()); + if (estimatedMaxFragSize > shc.sslConfig.maximumPacketSize) { + // For better interoperability, abort the maximum + // fragment length negotiation, rather than terminate + // the connection with a fatal alert. + if (SSLLogger.isOn && SSLLogger.isOn("ssl,handshake")) { + SSLLogger.fine( + "Abort the maximum fragment length negotiation, " + + "may overflow the maximum packet size limit."); + } + shc.maxFragmentLength = -1; + } + } + + // update the context + if (shc.maxFragmentLength > 0) { + shc.handshakeSession.setNegotiatedMaxFragSize( + shc.maxFragmentLength); + shc.conContext.inputRecord.changeFragmentSize( + shc.maxFragmentLength); + shc.conContext.outputRecord.changeFragmentSize( + shc.maxFragmentLength); + + // The response extension data is the same as the requested one. + shc.handshakeExtensions.put(SH_MAX_FRAGMENT_LENGTH, spec); + return new byte[] { spec.id }; + } + + return null; + } + } + + /** + * Network data consumer of a "max_fragment_length" extension in + * the ServerHello handshake message. + */ + private static final + class SHMaxFragmentLengthConsumer implements ExtensionConsumer { + // Prevent instantiation of this class. + private SHMaxFragmentLengthConsumer() { + // blank + } + + @Override + public void consume(ConnectionContext context, + HandshakeMessage message, ByteBuffer buffer) throws IOException { + + // The comsuming happens in client side only. + ClientHandshakeContext chc = (ClientHandshakeContext)context; + + // In response to "max_fragment_length" extension request only + MaxFragLenSpec requestedSpec = (MaxFragLenSpec) + chc.handshakeExtensions.get(CH_MAX_FRAGMENT_LENGTH); + if (requestedSpec == null) { + chc.conContext.fatal(Alert.UNEXPECTED_MESSAGE, + "Unexpected max_fragment_length extension in ServerHello"); + } + + // Parse the extension. + MaxFragLenSpec spec; + try { + spec = new MaxFragLenSpec(buffer); + } catch (IOException ioe) { + chc.conContext.fatal(Alert.UNEXPECTED_MESSAGE, ioe); + return; // fatal() always throws, make the compiler happy. + } + + if (spec.id != requestedSpec.id) { + chc.conContext.fatal(Alert.ILLEGAL_PARAMETER, + "The maximum fragment length response is not requested"); + } + + MaxFragLenEnum mfle = MaxFragLenEnum.valueOf(spec.id); + if (mfle == null) { + chc.conContext.fatal(Alert.ILLEGAL_PARAMETER, + "the requested maximum fragment length is other " + + "than the allowed values"); + } + + // update the context + chc.maxFragmentLength = mfle.fragmentSize; + chc.handshakeExtensions.put(SH_MAX_FRAGMENT_LENGTH, spec); + } + } + + /** + * After session creation consuming of a "max_fragment_length" + * extension in the ClientHello handshake message. + */ + private static final class SHMaxFragmentLengthUpdate + implements HandshakeConsumer { + + // Prevent instantiation of this class. + private SHMaxFragmentLengthUpdate() { + // blank + } + + @Override + public void consume(ConnectionContext context, + HandshakeMessage message) throws IOException { + // The comsuming happens in client side only. + ClientHandshakeContext chc = (ClientHandshakeContext)context; + + MaxFragLenSpec spec = (MaxFragLenSpec) + chc.handshakeExtensions.get(SH_MAX_FRAGMENT_LENGTH); + if (spec == null) { + // Ignore, no "max_fragment_length" extension response. + return; + } + + if ((chc.maxFragmentLength > 0) && + (chc.sslConfig.maximumPacketSize != 0)) { + int estimatedMaxFragSize = + chc.negotiatedCipherSuite.calculatePacketSize( + chc.maxFragmentLength, chc.negotiatedProtocol, + chc.sslContext.isDTLS()); + if (estimatedMaxFragSize > chc.sslConfig.maximumPacketSize) { + // For better interoperability, abort the maximum + // fragment length negotiation, rather than terminate + // the connection with a fatal alert. + if (SSLLogger.isOn && SSLLogger.isOn("ssl,handshake")) { + SSLLogger.fine( + "Abort the maximum fragment length negotiation, " + + "may overflow the maximum packet size limit."); + } + chc.maxFragmentLength = -1; + } + } + + // update the context + if (chc.maxFragmentLength > 0) { + chc.handshakeSession.setNegotiatedMaxFragSize( + chc.maxFragmentLength); + chc.conContext.inputRecord.changeFragmentSize( + chc.maxFragmentLength); + chc.conContext.outputRecord.changeFragmentSize( + chc.maxFragmentLength); + } + } + } + + /** + * Network data producer of a "max_fragment_length" extension in + * the EncryptedExtensions handshake message. + */ + private static final + class EEMaxFragmentLengthProducer implements HandshakeProducer { + // Prevent instantiation of this class. + private EEMaxFragmentLengthProducer() { + // blank + } + + @Override + public byte[] produce(ConnectionContext context, + HandshakeMessage message) throws IOException { + // The producing happens in server side only. + ServerHandshakeContext shc = (ServerHandshakeContext)context; + + // In response to "max_fragment_length" extension request only + MaxFragLenSpec spec = (MaxFragLenSpec) + shc.handshakeExtensions.get(CH_MAX_FRAGMENT_LENGTH); + if (spec == null) { + if (SSLLogger.isOn && SSLLogger.isOn("ssl,handshake")) { + SSLLogger.finest( + "Ignore unavailable max_fragment_length extension"); + } + return null; // ignore the extension + } + + if ((shc.maxFragmentLength > 0) && + (shc.sslConfig.maximumPacketSize != 0)) { + int estimatedMaxFragSize = + shc.negotiatedCipherSuite.calculatePacketSize( + shc.maxFragmentLength, shc.negotiatedProtocol, + shc.sslContext.isDTLS()); + if (estimatedMaxFragSize > shc.sslConfig.maximumPacketSize) { + // For better interoperability, abort the maximum + // fragment length negotiation, rather than terminate + // the connection with a fatal alert. + if (SSLLogger.isOn && SSLLogger.isOn("ssl,handshake")) { + SSLLogger.fine( + "Abort the maximum fragment length negotiation, " + + "may overflow the maximum packet size limit."); + } + shc.maxFragmentLength = -1; + } + } + + // update the context + if (shc.maxFragmentLength > 0) { + shc.handshakeSession.setNegotiatedMaxFragSize( + shc.maxFragmentLength); + shc.conContext.inputRecord.changeFragmentSize( + shc.maxFragmentLength); + shc.conContext.outputRecord.changeFragmentSize( + shc.maxFragmentLength); + + // The response extension data is the same as the requested one. + shc.handshakeExtensions.put(EE_MAX_FRAGMENT_LENGTH, spec); + return new byte[] { spec.id }; + } + + return null; + } + } + + /** + * Network data consumer of a "max_fragment_length" extension in the + * EncryptedExtensions handshake message. + */ + private static final + class EEMaxFragmentLengthConsumer implements ExtensionConsumer { + // Prevent instantiation of this class. + private EEMaxFragmentLengthConsumer() { + // blank + } + + @Override + public void consume(ConnectionContext context, + HandshakeMessage message, ByteBuffer buffer) throws IOException { + // The comsuming happens in client side only. + ClientHandshakeContext chc = (ClientHandshakeContext)context; + + // In response to "max_fragment_length" extension request only + MaxFragLenSpec requestedSpec = (MaxFragLenSpec) + chc.handshakeExtensions.get(CH_MAX_FRAGMENT_LENGTH); + if (requestedSpec == null) { + chc.conContext.fatal(Alert.UNEXPECTED_MESSAGE, + "Unexpected max_fragment_length extension in ServerHello"); + } + + // Parse the extension. + MaxFragLenSpec spec; + try { + spec = new MaxFragLenSpec(buffer); + } catch (IOException ioe) { + chc.conContext.fatal(Alert.UNEXPECTED_MESSAGE, ioe); + return; // fatal() always throws, make the compiler happy. + } + + if (spec.id != requestedSpec.id) { + chc.conContext.fatal(Alert.ILLEGAL_PARAMETER, + "The maximum fragment length response is not requested"); + } + + MaxFragLenEnum mfle = MaxFragLenEnum.valueOf(spec.id); + if (mfle == null) { + chc.conContext.fatal(Alert.ILLEGAL_PARAMETER, + "the requested maximum fragment length is other " + + "than the allowed values"); + } + + // update the context + chc.maxFragmentLength = mfle.fragmentSize; + chc.handshakeExtensions.put(EE_MAX_FRAGMENT_LENGTH, spec); + } + } + + /** + * After session creation consuming of a "max_fragment_length" + * extension in the EncryptedExtensions handshake message. + */ + private static final + class EEMaxFragmentLengthUpdate implements HandshakeConsumer { + // Prevent instantiation of this class. + private EEMaxFragmentLengthUpdate() { + // blank + } + + @Override + public void consume(ConnectionContext context, + HandshakeMessage message) throws IOException { + // The comsuming happens in client side only. + ClientHandshakeContext chc = (ClientHandshakeContext)context; + + MaxFragLenSpec spec = (MaxFragLenSpec) + chc.handshakeExtensions.get(EE_MAX_FRAGMENT_LENGTH); + if (spec == null) { + // Ignore, no "max_fragment_length" extension response. + return; + } + + if ((chc.maxFragmentLength > 0) && + (chc.sslConfig.maximumPacketSize != 0)) { + int estimatedMaxFragSize = + chc.negotiatedCipherSuite.calculatePacketSize( + chc.maxFragmentLength, chc.negotiatedProtocol, + chc.sslContext.isDTLS()); + if (estimatedMaxFragSize > chc.sslConfig.maximumPacketSize) { + // For better interoperability, abort the maximum + // fragment length negotiation, rather than terminate + // the connection with a fatal alert. + if (SSLLogger.isOn && SSLLogger.isOn("ssl,handshake")) { + SSLLogger.fine( + "Abort the maximum fragment length negotiation, " + + "may overflow the maximum packet size limit."); + } + chc.maxFragmentLength = -1; + } + } + + // update the context + if (chc.maxFragmentLength > 0) { + chc.handshakeSession.setNegotiatedMaxFragSize( + chc.maxFragmentLength); + chc.conContext.inputRecord.changeFragmentSize( + chc.maxFragmentLength); + chc.conContext.outputRecord.changeFragmentSize( + chc.maxFragmentLength); + } + } + } +}