package org.bouncycastle.crypto.tls;

import java.io.IOException;
import java.security.SecureRandom;
import java.util.Vector;

public class DTLSServerProtocol extends DTLSProtocol {

    protected boolean verifyRequests = true;

    public DTLSServerProtocol(SecureRandom secureRandom) {
        super(secureRandom);
    }

    public boolean getVerifyRequests() {
        return verifyRequests;
    }

    public void setVerifyRequests(boolean verifyRequests) {
        this.verifyRequests = verifyRequests;
    }

    public DTLSTransport connect(TlsServer server, DatagramTransport transport) throws IOException {

        if (server == null)
            throw new IllegalArgumentException("'server' cannot be null");
        if (transport == null)
            throw new IllegalArgumentException("'transport' cannot be null");

        ServerHandshakeState state = new ServerHandshakeState();
        state.server = server;
        state.serverContext = new TlsServerContextImpl(secureRandom, new SecurityParameters());
        state.serverContext.getSecurityParameters().serverRandom = TlsProtocol
            .createRandomBlock(secureRandom);
        server.init(state.serverContext);

        DTLSRecordLayer recordLayer = new DTLSRecordLayer(transport, state.serverContext,
            ContentType.handshake);

        // TODO Need to handle sending of HelloVerifyRequest without entering a full connection

        DTLSReliableHandshake handshake = new DTLSReliableHandshake(recordLayer);

        DTLSReliableHandshake.Message clientMessage = handshake.receiveMessage();

        {
            // NOTE: After receiving a record from the client, we discover the record layer version
            ProtocolVersion client_version = recordLayer.getDiscoveredPeerVersion();
            // TODO Read RFCs for guidance on the expected record layer version number
            state.serverContext.setClientVersion(client_version);
        }

        if (clientMessage.getType() == HandshakeType.client_hello) {
            processClientHello(state, clientMessage.getBody());
            clientMessage = handshake.receiveMessage();
        } else {
            // TODO Alert
        }

        // TODO Send ServerHello

        Vector serverSupplementalData = state.server.getServerSupplementalData();
        if (serverSupplementalData != null) {
            byte[] supplementalDataBody = generateSupplementalData(serverSupplementalData);
            handshake.sendMessage(HandshakeType.supplemental_data, supplementalDataBody);
        }

        return null;
    }

    protected void processClientHello(ServerHandshakeState state, byte[] body) throws IOException {
        // TODO
    }

    protected static class ServerHandshakeState {
        TlsServer server = null;
        TlsServerContextImpl serverContext = null;
        // int[] offeredCipherSuites = null;
        // short[] offeredCompressionMethods = null;
        // Hashtable clientExtensions = null;
        // boolean secure_renegotiation = false;
        // TlsKeyExchange keyExchange = null;
        // TlsAuthentication authentication = null;
        // CertificateRequest certificateRequest = null;
        // TlsCredentials clientCredentials = null;
    }
}

@@ -2610,19 +2610,1268 @@
     
-return null
+// TODO Send Certificate%0D%0A%0D%0A        // TODO Send ServerKeyExchange%0D%0A%0D%0A        // TODO Send CertificateRequest%0D%0A%0D%0A        // TODO Send ServerHelloDone%0D%0A%0D%0A        // TODO Lots more...%0D%0A        %0D%0A        recordLayer.initPendingEpoch(state.server.getCipher());%0D%0A%0D%0A        // NOTE: Calculated exclusive of the actual Finished message from the client%0D%0A        byte%5B%5D expectedClientVerifyData = TlsUtils.calculateVerifyData(state.serverContext,%0D%0A            %22client finished%22, handshake.getCurrentHash());%0D%0A        clientMessage = handshake.receiveMessage();%0D%0A%0D%0A        if (clientMessage.getType() == HandshakeType.finished) %7B%0D%0A            processFinished(clientMessage.getBody(), expectedClientVerifyData);%0D%0A        %7D else %7B%0D%0A            // TODO Alert%0D%0A        %7D%0D%0A%0D%0A        // NOTE: Calculated exclusive of the Finished message itself%0D%0A        byte%5B%5D serverVerifyData = TlsUtils.calculateVerifyData(state.serverContext,%0D%0A            %22server finished%22, handshake.getCurrentHash());%0D%0A        handshake.sendMessage(HandshakeType.finished, serverVerifyData);%0D%0A%0D%0A        // TODO Need an alternative here that supports resending of our final flight%0D%0A        handshake.finish();%0D%0A%0D%0A        recordLayer.handshakeSuccessful();%0D%0A%0D%0A        return new DTLSTransport(recordLayer)
 ;%0D%0A 

Add finished message exchange and verification