iaik.security.ssl
Class ALPNProtocolName

java.lang.Object
  extended by iaik.security.ssl.ALPNProtocolName
All Implemented Interfaces:
java.lang.Cloneable

public class ALPNProtocolName
extends java.lang.Object
implements java.lang.Cloneable

This class represents a ProtocolName as used by the TLS application_layer_protocol_negotiation extension (see RFC 7301).

The application_layer_protocol_negotiation (ALPN) extension allows to negotiate the application layer protocol within the TLS handshake. For doing so the client sends an ALPN extension containing the names of the application layer protocols it supports (in preference order). The server compares the protocol names got from the client with its locally configured list and sends back an ALPN extension containing the first of its protocol names that matches to any of the protocol names received from the client. If the server does not support any of the client protocols it sends back a fatal "NO APPLICATION PROTOCOL" alert.

RFC 7301 defines an ALPN ProtocolName as opaque, non-empty byte string identifying the protocol name:

   opaque ProtocolName<1..2^8-1>;

  struct {
      ProtocolName protocol_name_list<2..2^16-1>
  } ProtocolNameList;
 

When creating an ALPNProtocolName object the encoded and/or not encoded name value have to be specified, e.g.:

 String protocolName = ...;
 byte[] encodedProtocolName = ...;
 ALPNProtocolName protocolName = new ALPNProtocolName(protocolName, encodedProtocolName);
 
If the encoded name is not specified it is UTF-8 encoding before sent to the peer. If the name is not specified the encoded name is UTF-8 decoded.

For getting the (String or encoded) representation from a ALPNProtocolName object, use method getName or getEncodedName, respectively, e.g.:

 String name = protocolName.getName();
 

On the client side you will use the ALPNProtocolName class to build an ALPNProtocolNameList to be sent to the server. You can create ALPNProtocolName objects on your own or use any of the predefined names e.g.:

 // create protocol name list for http/1.1 and http/2
 ALPNProtocolName[] protocolNames = { ALPNProtocolName.PN_HTTP_11, ALPNProtocolName.PN_H_2 };
 ALPNProtocolNameList protocolNameList = new ALPNProtocolNameList(protocolNames);
 // add to ExtensionList
 ExtensionList extensions = new ExtensionList();
 ...
 extensions.addExtension(protocolNameList);
 ...
 // set extensions for the SSLClientContext configuration:
 SSLClientContext clientContext = new SSLClientContext();
 ...
 clientContext.setExtensions(extensions);
 ...
 
When having finished the handshake you may get the negotiated protocol name by asking the SSLSocket for the ProtocolNameList included in the active extension list (extensions negotiated between client and server) or in the peer extension list (extensions got from the server). Since the server is only allowed to send an ALPN extension containing one protocol name only, the ALPNProtocolNameList got from the active extension list should be equal to the one got from the peer extension list (if the server has sent back an ALPN extension):
 SSLContext clientContext = ...;
 ...
 // set extensions (including ALPN)
 ...
 String serverName = ...;
 int serverPort = ...;
 // create SSLSocket, perform handshake, e.g.:
 SSLSocket sslSocket = new SSLSocket(serverName, serverPort, clientContext);
 sslSocket.startHandshake();
 ...
 // get ALPN extension and protocol name sent by the server:
 ExtensionList activeExtensions = socket.getActiveExtensions();
 if (activeExtensions != null) {
   ALPNProtocolNameList protocolNameList = (ALPNProtocolNameList)activeExtensions.getExtension(ALPNProtocolNameList.TYPE);
   if (protocolNameList != null) {
     ALPNProtocolName[] protocolNames = protocolNameList.getProtocolNames();
     System.out.println("Using ALPN protocol: " + protocolNames[0]);
   }
 }
 
On the server side you may use the ALPNProtocolName class to build an ALPNProtocolNameList to tell the server which protocol names may be accepted from the client e.g.:
 // create protocol name list for http/1.1 and http/2
 ALPNProtocolName[] protocolNames = { ALPNProtocolName.PN_HTTP_11, ALPNProtocolName.PN_H_2 };
 ALPNProtocolNameList protocolNameList = new ALPNProtocolNameList(protocolNames);
 // add to ExtensionList
 ExtensionList extensions = new ExtensionList();
 ...
 extensions.addExtension(protocolNameList);
 ...
 // set extensions for the SSLServerContext configuration:
 SSLServerContext serverContext = new SSLServerContext();
 ...
 serverContext.setExtensions(extensions);
 ...
 

See Also:
ALPNProtocolNameList

Field Summary
static ALPNProtocolName PN_H_2
          ProtocolName http/2 (h2) (0x68 0x32).
static ALPNProtocolName PN_HTTP_11
          ProtocolName http/1.1 (0x68 0x74 0x74 0x70 0x2f 0x31 0x2e 0x31).
static ALPNProtocolName PN_SPDY_1
          ProtocolName spdy/1 (0x68 0x74 0x74 0x70 0x2f 0x31 0x2e 0x31).
static ALPNProtocolName PN_SPDY_2
          ProtocolName spdy/2 (0x68 0x74 0x74 0x70 0x2f 0x31 0x2e 0x31).
 
Constructor Summary
ALPNProtocolName(byte[] encodedName)
          Creates a new ALPN ProtocolName for the given encoded protocol name.
ALPNProtocolName(java.lang.String name)
          Creates a new ALPN ProtocolName for the given protocol name.
ALPNProtocolName(java.lang.String name, byte[] encodedName)
          Creates a new ALPN ProtocolName from given name and encoded name.
 
Method Summary
 java.lang.Object clone()
          Gets a clone of this ProtocolName.
 boolean equals(java.lang.Object obj)
          Checks if this ProtocolName is equal to the given object.
 byte[] getEncodedName()
          Gets the encoded protocol name.
 java.lang.String getName()
          Gets the protocol name as String.
 int hashCode()
          Gets a hash code of this ProtocolName.
 java.lang.String toString()
          Gets a String representation of this ProtocolName.
 
Methods inherited from class java.lang.Object
finalize, getClass, notify, notifyAll, wait, wait, wait
 

Field Detail

PN_HTTP_11

public static final ALPNProtocolName PN_HTTP_11
ProtocolName http/1.1 (0x68 0x74 0x74 0x70 0x2f 0x31 0x2e 0x31).


PN_H_2

public static final ALPNProtocolName PN_H_2
ProtocolName http/2 (h2) (0x68 0x32).


PN_SPDY_1

public static final ALPNProtocolName PN_SPDY_1
ProtocolName spdy/1 (0x68 0x74 0x74 0x70 0x2f 0x31 0x2e 0x31).


PN_SPDY_2

public static final ALPNProtocolName PN_SPDY_2
ProtocolName spdy/2 (0x68 0x74 0x74 0x70 0x2f 0x31 0x2e 0x31).

Constructor Detail

ALPNProtocolName

public ALPNProtocolName(byte[] encodedName)
Creates a new ALPN ProtocolName for the given encoded protocol name.

Parameters:
encodedName - the (e.g. UTF-8) encoded protocol name (identification sequence) (the encodedName byte array is not cloned or copied by this constructor)

ALPNProtocolName

public ALPNProtocolName(java.lang.String name)
                 throws java.io.UnsupportedEncodingException
Creates a new ALPN ProtocolName for the given protocol name.

Parameters:
name - the protocol name as String (will be UTF-8 encoded)
Throws:
java.io.UnsupportedEncodingException - if an error occurs when trying to encode the name
java.lang.IllegalArgumentException - if the given protocolName represents an ipAddress

ALPNProtocolName

public ALPNProtocolName(java.lang.String name,
                        byte[] encodedName)
                 throws java.io.UnsupportedEncodingException
Creates a new ALPN ProtocolName from given name and encoded name.

Both name and encodedName are not allowed to be null. If encodedName is null the given name String is UTF-8 encoded. If name is null this default implementation tries to UTF-8 decode the given encoded name when method getName is called.

Parameters:
name - the protocol name as String; maybe null if encodedName is not null
encodedName - the (e.g. UTF-8) encoded protocol name (identification sequence); maybe null if name is not null. (the encodedName array is not cloned or copied by this method)
Throws:
java.lang.IllegalArgumentException - if encodedName is greater than 2^8-1, or if name and encodedName are both null
java.io.UnsupportedEncodingException - if an error occurs when trying to encode the name (if encodedName is null)
Method Detail

getName

public java.lang.String getName()
                         throws java.io.UnsupportedEncodingException
Gets the protocol name as String.

Returns:
the protocol name as String.
Throws:
java.io.UnsupportedEncodingException - if an error occurs when trying to decode the protocol name to get its String representation (if it has not been decoded so far)

getEncodedName

public byte[] getEncodedName()
                      throws java.io.UnsupportedEncodingException
Gets the encoded protocol name.

Returns:
the encoded protocol name (the returned byte array is not cloned or copied by this method)
Throws:
java.io.UnsupportedEncodingException - if an error occurs when trying to (UTF-8) encode the name (if it has not been encoded yet)

hashCode

public int hashCode()
Gets a hash code of this ProtocolName.

Overrides:
hashCode in class java.lang.Object
Returns:
a hash code of this ProtocolName

equals

public boolean equals(java.lang.Object obj)
Checks if this ProtocolName is equal to the given object. This method checks of the encoded name representations are equal. If only String representations of the names are available this method performs a case insensitive comparison of the name strings.

Overrides:
equals in class java.lang.Object
Returns:
true if this ProtocolName is equal to the given object, false if it is not equal to it

clone

public java.lang.Object clone()
Gets a clone of this ProtocolName.

Overrides:
clone in class java.lang.Object
Returns:
a clone of this ProtocolName

toString

public java.lang.String toString()
Gets a String representation of this ProtocolName.

Overrides:
toString in class java.lang.Object
Returns:
a String representation of this ProtocolName

This Javadoc may contain text parts from text parts from IETF Internet Standard specifications (see copyright note).

iSaSiLk 6.0, (c) 2002 IAIK, (c) 2003 - 2015 SIC