All Downloads are FREE. Search and download functionalities are using the official Maven repository.

sun.security.ssl.ALPNExtension Maven / Gradle / Ivy

There is a newer version: 8.1.13.v20181017
Show newest version
/*
 * Copyright (c) 2014, Mort Bay Consulting Pty. Ltd. 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.  Mort Bay Consulting designates this
 * particular file as subject to the "Classpath" exception as provided
 * by Mort Bay Consulting 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).
 */

package sun.security.ssl;

import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.nio.charset.StandardCharsets;
import java.util.ArrayList;
import java.util.List;

import javax.net.ssl.SSLProtocolException;

public class ALPNExtension extends HelloExtension
{
    private static final int ID = ExtensionType.EXT_ALPN.id;

    private final List protocols = new ArrayList<>();
    private final byte[] content;

    public ALPNExtension(List protocols) throws SSLProtocolException
    {
        super(ExtensionType.get(ID));
        this.protocols.addAll(protocols);
        content = init();
    }

    public ALPNExtension(HandshakeInStream input, int length) throws IOException
    {
        super(ExtensionType.get(ID));
        length = input.getInt16();
        while (length > 0)
        {
            byte[] protocolBytes = input.getBytes8();
            protocols.add(new String(protocolBytes, StandardCharsets.UTF_8));
            length -= 1 + protocolBytes.length;
        }
        content = init();
    }

    private byte[] init() throws SSLProtocolException
    {
        ByteArrayOutputStream bytes = new ByteArrayOutputStream();
        for (String protocol : protocols)
        {
            byte[] protocolBytes = protocol.getBytes(StandardCharsets.UTF_8);
            int length = protocolBytes.length;
            if (length > 255)
                throw new SSLProtocolException("Protocol name too long: " + protocol);
            bytes.write(length);
            bytes.write(protocolBytes, 0, length);
        }
        byte[] protocolsBytes = bytes.toByteArray();
        byte[] result = new byte[2 + protocolsBytes.length];
        result[0] = (byte)((protocolsBytes.length & 0xFF00) >> 8);
        result[1] = (byte)(protocolsBytes.length & 0xFF);
        System.arraycopy(protocolsBytes, 0, result, 2, protocolsBytes.length);
        return result;
    }

    public List getProtocols()
    {
        return protocols;
    }

    @Override
    int length()
    {
        return 2 + 2 + content.length;
    }

    @Override
    void send(HandshakeOutStream out) throws IOException
    {
        out.putInt16(ID);
        out.putInt16(content.length);
        out.write(content, 0, content.length);
    }

    @Override
    public String toString()
    {
        return String.format("Extension %s, protocols: %s", type, protocols);
    }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy