/*
 *  Licensed to the Apache Software Foundation (ASF) under one
 *  or more contributor license agreements.  See the NOTICE file
 *  distributed with this work for additional information
 *  regarding copyright ownership.  The ASF licenses this file
 *  to you under the Apache License, Version 2.0 (the
 *  "License"); you may not use this file except in compliance
 *  with the License.  You may obtain a copy of the License at
 *
 *    http://www.apache.org/licenses/LICENSE-2.0
 *
 *  Unless required by applicable law or agreed to in writing,
 *  software distributed under the License is distributed on an
 *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 *  KIND, either express or implied.  See the License for the
 *  specific language governing permissions and limitations
 *  under the License.
 *
 */
package org.apache.directory.shared.kerberos.components;


import java.nio.ByteBuffer;
import java.util.ArrayList;
import java.util.LinkedHashSet;
import java.util.List;
import java.util.Set;

import org.apache.directory.api.asn1.Asn1Object;
import org.apache.directory.api.asn1.EncoderException;
import org.apache.directory.api.asn1.ber.tlv.BerValue;
import org.apache.directory.api.asn1.ber.tlv.TLV;
import org.apache.directory.api.asn1.ber.tlv.UniversalTag;
import org.apache.directory.api.util.Strings;
import org.apache.directory.server.i18n.I18n;
import org.apache.directory.shared.kerberos.KerberosConstants;
import org.apache.directory.shared.kerberos.KerberosTime;
import org.apache.directory.shared.kerberos.codec.options.KdcOptions;
import org.apache.directory.shared.kerberos.codec.types.EncryptionType;
import org.apache.directory.shared.kerberos.messages.Ticket;


/**
 * The KDC-REQ-BODY data structure. It will store the object described by the ASN.1 grammar :
 * <pre>
 * KDC-REQ-BODY    ::= SEQUENCE {
 *      kdc-options             [0] KDCOptions,
 *      cname                   [1] PrincipalName OPTIONAL
 *                                  -- Used only in AS-REQ --,
 *      realm                   [2] Realm
 *                                  -- Server's realm
 *                                  -- Also client's in AS-REQ --,
 *      sname                   [3] PrincipalName OPTIONAL,
 *      from                    [4] KerberosTime OPTIONAL,
 *      till                    [5] KerberosTime,
 *      rtime                   [6] KerberosTime OPTIONAL,
 *      nonce                   [7] UInt32,
 *      etype                   [8] SEQUENCE OF Int32 -- EncryptionType
 *                                  -- in preference order --,
 *      addresses               [9] HostAddresses OPTIONAL,
 *      enc-authorization-data  [10] EncryptedData OPTIONAL
 *                                  -- AuthorizationData --,
 *      additional-tickets      [11] SEQUENCE OF Ticket OPTIONAL
 *                                      -- NOTE: not empty
 * }
 * </pre>
 * @author <a href="mailto:dev@directory.apache.org">Apache Directory Project</a>
 */
public class KdcReqBody implements Asn1Object
{
    /** The KDC options */
    private KdcOptions kdcOptions;

    /** The Client Principal, if the request is an AS-REQ */
    private PrincipalName cName;

    /** The realm */
    private String realm;

    /** The Server Principal */
    private PrincipalName sName;

    /** The start time for the requested ticket */
    private KerberosTime from;

    /** The expiration date for the requested ticket */
    private KerberosTime till;

    /** The renew-till date for the requested ticket */
    private KerberosTime rtime;

    /** Random number to avoid MiM attacks */
    private int nonce;

    /** Set of desired encryption types */
    private Set<EncryptionType> eType;

    /** Addresses valid for the requested ticket */
    private HostAddresses addresses;

    /** Encoded authorizationData, used by the TGS-REQ only */
    private EncryptedData encAuthorizationData;

    /** Additional tickets */
    private List<Ticket> additionalTickets;

    // Storage for computed lengths
    private int kdcOptionsLength;
    private int cNameLength;
    private int realmLength;
    private byte[] realmBytes;
    private int sNameLength;
    private int fromLength;
    private int tillLength;
    private int rtimeLength;
    private int nonceLength;
    private int eTypeLength;
    private int eTypeSeqLength;
    private int[] eTypeLengths;
    private int addressesLength;
    private int encAuthzDataLength;
    private int additionalTicketLength;
    private int additionalTicketSeqLength;
    private int[] additionalTicketsLengths;
    private int kdcReqBodySeqLength;
    private int kdcReqBodyLength;


    /**
     * Creates a new instance of RequestBody.
     */
    public KdcReqBody()
    {
        additionalTickets = new ArrayList<>();
        eType = new LinkedHashSet<>();
    }


    /**
     * Returns the additional {@link Ticket}s.
     *
     * @return The additional {@link Ticket}s.
     */
    public Ticket[] getAdditionalTickets()
    {
        return additionalTickets.toArray( new Ticket[]
            {} );
    }


    /**
     * Set the list of additional Ticket
     * @param additionalTickets the additionalTickets to set
     */
    public void setAdditionalTickets( List<Ticket> additionalTickets )
    {
        this.additionalTickets = additionalTickets;
    }


    /**
     * Add a new Ticket to the list of additional tickets
     * @param additionalTicket the additionalTicket to set
     */
    public void addAdditionalTicket( Ticket additionalTicket )
    {
        this.additionalTickets.add( additionalTicket );
    }


    /**
     * Returns the {@link HostAddresses}.
     *
     * @return The {@link HostAddresses}.
     */
    public HostAddresses getAddresses()
    {
        return addresses;
    }


    /**
     * @param addresses the addresses to set
     */
    public void setAddresses( HostAddresses addresses )
    {
        this.addresses = addresses;
    }


    /**
     * @return the client PrincipalName
     */
    public PrincipalName getCName()
    {
        return cName;
    }


    /**
     * @param cName the cName to set
     */
    public void setCName( PrincipalName cName )
    {
        this.cName = cName;
    }


    /**
     * Returns the encrypted {@link AuthorizationData} as {@link EncryptedData}.
     *
     * @return The encrypted {@link AuthorizationData} as {@link EncryptedData}.
     */
    public EncryptedData getEncAuthorizationData()
    {
        return encAuthorizationData;
    }


    /**
     * @param encAuthorizationData the encAuthorizationData to set
     */
    public void setEncAuthorizationData( EncryptedData encAuthorizationData )
    {
        this.encAuthorizationData = encAuthorizationData;
    }


    /**
     * Returns the requested {@link EncryptionType}s.
     *
     * @return The requested {@link EncryptionType}s.
     */
    public Set<EncryptionType> getEType()
    {
        return eType;
    }


    /**
     * @param eType the eType to set
     */
    public void setEType( Set<EncryptionType> eType )
    {
        this.eType = eType;
    }


    /**
     * @param eType the eType to add
     */
    public void addEType( EncryptionType eType )
    {
        this.eType.add( eType );
    }


    /**
     * Returns the from {@link KerberosTime}.
     *
     * @return The from {@link KerberosTime}.
     */
    public KerberosTime getFrom()
    {
        return from;
    }


    /**
     * @param from the from to set
     */
    public void setFrom( KerberosTime from )
    {
        this.from = from;
    }


    /**
     * Returns the {@link KdcOptions}.
     *
     * @return The {@link KdcOptions}.
     */
    public KdcOptions getKdcOptions()
    {
        return kdcOptions;
    }


    /**
     * @param kdcOptions the kdcOptions to set
     */
    public void setKdcOptions( KdcOptions kdcOptions )
    {
        this.kdcOptions = kdcOptions;
    }


    /**
     * Returns the nonce.
     *
     * @return The nonce.
     */
    public int getNonce()
    {
        return nonce;
    }


    /**
     * @param nonce the nonce to set
     */
    public void setNonce( int nonce )
    {
        this.nonce = nonce;
    }


    /**
     * @return the realm
     */
    public String getRealm()
    {
        return realm;
    }


    /**
     * @param realm the realm to set
     */
    public void setRealm( String realm )
    {
        this.realm = realm;
    }


    /**
     * Returns the RenewTime {@link KerberosTime}.
     *
     * @return The RenewTime {@link KerberosTime}.
     */
    public KerberosTime getRTime()
    {
        return rtime;
    }


    /**
     * @param rtime the renewTime to set
     */
    public void setRtime( KerberosTime rtime )
    {
        this.rtime = rtime;
    }


    /**
     * Returns the server {@link PrincipalName}.
     *
     * @return The server {@link PrincipalName}.
     */
    public PrincipalName getSName()
    {
        return sName;
    }


    /**
     * @param sName the sName to set
     */
    public void setSName( PrincipalName sName )
    {
        this.sName = sName;
    }


    /**
     * Returns the till {@link KerberosTime}.
     *
     * @return The till {@link KerberosTime}.
     */
    public KerberosTime getTill()
    {
        return till;
    }


    /**
     * @param till the till to set
     */
    public void setTill( KerberosTime till )
    {
        this.till = till;
    }


    /**
     * Compute the KdcReqBody length
     * <pre>
     * KdcReqBody :
     *
     * 0x30 L1 KdcReqBody sequence
     *  |
     *  +--&gt; 0xA0 L2 kdc-options tag
     *  |     |
     *  |     +--&gt; 0x03 L2-1 kdc-options (BitString)
     *  |
     *  +--&gt; 0xA1 L3 cname tag
     *  |     |
     *  |     +--&gt; 0x30 L3-1 cname (PrincipalName)
     *  |
     *  +--&gt; 0xA2 L4 realm tag
     *  |     |
     *  |     +--&gt; 0x1B L4-1 realm (Realm, KerberosString)
     *  |
     *  +--&gt; 0xA3 L5 sname tag
     *  |     |
     *  |     +--&gt; 0x30 L5-1 sname (PrincipalName)
     *  |
     *  +--&gt; 0xA4 L6 from tag
     *  |     |
     *  |     +--&gt; 0x18 L6-1 from (KerberosTime)
     *  |
     *  +--&gt; 0xA5 L7 till tag
     *  |     |
     *  |     +--&gt; 0x18 L7-1 till (KerberosTime)
     *  |
     *  +--&gt; 0xA6 L8 rtime tag
     *  |     |
     *  |     +--&gt; 0x18 L8-1 rtime (KerberosTime)
     *  |
     *  +--&gt; 0xA7 L9 nonce tag
     *  |     |
     *  |     +--&gt; 0x02 L9-1 nonce (Int)
     *  |
     *  +--&gt; 0xA8 L10 etype tag
     *  |     |
     *  |     +--&gt; 0x30 L10-1 SEQ
     *  |           |
     *  |           +--&gt; 0x02 L10-1-1 etype
     *  |           |
     *  |           +--&gt; 0x02 L10-1-2 etype
     *  |           |
     *  |           :
     *  |
     *  +--&gt; 0xA9 L11 addresses tag
     *  |     |
     *  |     +--&gt; 0x30 L11-1 addresses (HostAddresses)
     *  |
     *  +--&gt; 0xAA L12 enc-authorization-data tag
     *  |     |
     *  |     +--&gt; 0x30 L12-1 enc-authorization-data
     *  |
     *  +--&gt; 0xAB L13 additional-tickets tag
     *        |
     *        +--&gt; 0x30 L13-1 additional-tickets
     *              |
     *              +--&gt; 0x61 L13-1-1 Ticket
     *              |
     *              +--&gt; 0x61 L13-1-2 Ticket
     *              |
     *              :
     * </pre>
     */
    @Override
    public int computeLength()
    {
        reset();

        // The KdcOptions length
        kdcOptionsLength = 1 + 1 + kdcOptions.getBytes().length;
        kdcReqBodySeqLength = 1 + TLV.getNbBytes( kdcOptionsLength ) + kdcOptionsLength;

        // The cname length
        if ( cName != null )
        {
            cNameLength = cName.computeLength();
            kdcReqBodySeqLength += 1 + TLV.getNbBytes( cNameLength ) + cNameLength;
        }

        // Compute the realm length.
        realmBytes = Strings.getBytesUtf8( realm );
        realmLength = 1 + TLV.getNbBytes( realmBytes.length ) + realmBytes.length;
        kdcReqBodySeqLength += 1 + TLV.getNbBytes( realmLength ) + realmLength;

        // The sname length
        if ( sName != null )
        {
            sNameLength = sName.computeLength();
            kdcReqBodySeqLength += 1 + TLV.getNbBytes( sNameLength ) + sNameLength;
        }

        // The from length
        if ( from != null )
        {
            fromLength = 1 + 1 + 0x0F;
            kdcReqBodySeqLength += 1 + 1 + fromLength;
        }

        // The till length
        tillLength = 1 + 1 + 0x0F;
        kdcReqBodySeqLength += 1 + 1 + tillLength;

        // The rtime length
        if ( rtime != null )
        {
            rtimeLength = 1 + 1 + 0x0F;
            kdcReqBodySeqLength += 1 + 1 + rtimeLength;
        }

        // The nonce length
        nonceLength = 1 + 1 + BerValue.getNbBytes( nonce );
        kdcReqBodySeqLength += 1 + 1 + nonceLength;

        // The eType length
        eTypeLengths = new int[eType.size()];
        int pos = 0;
        eTypeSeqLength = 0;

        for ( EncryptionType encryptionType : eType )
        {
            eTypeLengths[pos] = 1 + 1 + BerValue.getNbBytes( encryptionType.getValue() );
            eTypeSeqLength += eTypeLengths[pos];
            pos++;
        }

        eTypeLength = 1 + TLV.getNbBytes( eTypeSeqLength ) + eTypeSeqLength;
        kdcReqBodySeqLength += 1 + TLV.getNbBytes( eTypeLength ) + eTypeLength;

        // The Addresses length
        if ( addresses != null )
        {
            addressesLength = addresses.computeLength();
            kdcReqBodySeqLength += 1 + TLV.getNbBytes( addressesLength ) + addressesLength;
        }

        // The EncAuthorizationData length
        if ( encAuthorizationData != null )
        {
            encAuthzDataLength = encAuthorizationData.computeLength();
            kdcReqBodySeqLength += 1 + TLV.getNbBytes( encAuthzDataLength ) + encAuthzDataLength;
        }

        // The additionalTickets length
        if ( !additionalTickets.isEmpty() )
        {
            additionalTicketsLengths = new int[additionalTickets.size()];
            additionalTicketSeqLength = 0;
            pos = 0;

            for ( Ticket ticket : additionalTickets )
            {
                additionalTicketsLengths[pos] = ticket.computeLength();
                additionalTicketSeqLength += additionalTicketsLengths[pos];
                pos++;
            }

            additionalTicketLength = 1 + TLV.getNbBytes( additionalTicketSeqLength ) + additionalTicketSeqLength;
            kdcReqBodySeqLength += 1 + TLV.getNbBytes( additionalTicketLength ) + additionalTicketLength;
        }

        // compute the global size
        kdcReqBodyLength = 1 + TLV.getNbBytes( kdcReqBodySeqLength ) + kdcReqBodySeqLength;

        return kdcReqBodyLength;
    }


    /**
     * Encode the KDC-REQ-BODY component
     *
     * @param buffer The buffer containing the encoded result
     * @return The encoded component
     * @throws EncoderException If the encoding failed
     */
    @Override
    public ByteBuffer encode( ByteBuffer buffer ) throws EncoderException
    {
        if ( buffer == null )
        {
            throw new EncoderException( I18n.err( I18n.ERR_148 ) );
        }

        // The KDC-REQ-BODY SEQ Tag
        buffer.put( UniversalTag.SEQUENCE.getValue() );
        buffer.put( TLV.getBytes( kdcReqBodySeqLength ) );

        // The KdcOptions -----------------------------------------------------
        // The tag
        buffer.put( ( byte ) KerberosConstants.KDC_REQ_BODY_KDC_OPTIONS_TAG );
        buffer.put( TLV.getBytes( kdcOptionsLength ) );

        // The value
        BerValue.encode( buffer, kdcOptions );

        // The cname if any ---------------------------------------------------
        if ( cName != null )
        {
            // The tag
            buffer.put( ( byte ) KerberosConstants.KDC_REQ_BODY_CNAME_TAG );
            buffer.put( TLV.getBytes( cNameLength ) );

            // The value
            cName.encode( buffer );
        }

        // The realm ----------------------------------------------------------
        // The tag
        buffer.put( ( byte ) KerberosConstants.KDC_REQ_BODY_REALM_TAG );
        buffer.put( TLV.getBytes( realmLength ) );

        // The value
        buffer.put( UniversalTag.GENERAL_STRING.getValue() );
        buffer.put( TLV.getBytes( realmBytes.length ) );
        buffer.put( realmBytes );

        // The sname, if any --------------------------------------------------
        if ( sName != null )
        {
            // The tag
            buffer.put( ( byte ) KerberosConstants.KDC_REQ_BODY_SNAME_TAG );
            buffer.put( TLV.getBytes( sNameLength ) );

            // The value
            sName.encode( buffer );
        }

        // The from, if any ---------------------------------------------------
        if ( from != null )
        {
            // The tag
            buffer.put( ( byte ) KerberosConstants.KDC_REQ_BODY_FROM_TAG );
            buffer.put( TLV.getBytes( fromLength ) );

            // The value
            buffer.put( UniversalTag.GENERALIZED_TIME.getValue() );
            buffer.put( ( byte ) 0x0F );
            buffer.put( from.getBytes() );
        }

        // The till -----------------------------------------------------------
        // The tag
        buffer.put( ( byte ) KerberosConstants.KDC_REQ_BODY_TILL_TAG );
        buffer.put( TLV.getBytes( tillLength ) );

        // The value
        buffer.put( UniversalTag.GENERALIZED_TIME.getValue() );
        buffer.put( ( byte ) 0x0F );
        buffer.put( till.getBytes() );

        // The rtime if any ---------------------------------------------------
        if ( rtime != null )
        {
            // The tag
            buffer.put( ( byte ) KerberosConstants.KDC_REQ_BODY_RTIME_TAG );
            buffer.put( TLV.getBytes( rtimeLength ) );

            // The value
            buffer.put( UniversalTag.GENERALIZED_TIME.getValue() );
            buffer.put( ( byte ) 0x0F );
            buffer.put( rtime.getBytes() );
        }

        // The nonce ----------------------------------------------------------
        // The tag
        buffer.put( ( byte ) KerberosConstants.KDC_REQ_BODY_NONCE_TAG );
        buffer.put( TLV.getBytes( nonceLength ) );

        // The value
        BerValue.encode( buffer, nonce );

        // The etype ----------------------------------------------------------
        // The tag
        buffer.put( ( byte ) KerberosConstants.KDC_REQ_BODY_ETYPE_TAG );
        buffer.put( TLV.getBytes( eTypeLength ) );

        // The sequence
        buffer.put( UniversalTag.SEQUENCE.getValue() );
        buffer.put( TLV.getBytes( eTypeSeqLength ) );

        // The values
        for ( EncryptionType encryptionType : eType )
        {
            BerValue.encode( buffer, encryptionType.getValue() );
        }

        // The addresses if any -----------------------------------------------
        if ( addresses != null )
        {
            // The tag
            buffer.put( ( byte ) KerberosConstants.KDC_REQ_BODY_ADDRESSES_TAG );
            buffer.put( TLV.getBytes( addressesLength ) );

            // The value
            addresses.encode( buffer );
        }

        // The enc-authorization-data, if any ---------------------------------
        if ( encAuthorizationData != null )
        {
            // The tag
            buffer.put( ( byte ) KerberosConstants.KDC_REQ_BODY_ENC_AUTHZ_DATA_TAG );
            buffer.put( TLV.getBytes( encAuthzDataLength ) );

            // The value
            encAuthorizationData.encode( buffer );
        }

        // The additional-tickets, if any -------------------------------------
        if ( !additionalTickets.isEmpty() )
        {
            // The tag
            buffer.put( ( byte ) KerberosConstants.KDC_REQ_BODY_ADDITIONAL_TICKETS_TAG );
            buffer.put( TLV.getBytes( additionalTicketLength ) );

            // The sequence
            buffer.put( UniversalTag.SEQUENCE.getValue() );
            buffer.put( TLV.getBytes( additionalTicketSeqLength ) );

            // The values
            for ( Ticket ticket : additionalTickets )
            {
                ticket.encode( buffer );
            }
        }

        return buffer;
    }


    /**
     * reset the fields used while computing length
     */
    private void reset()
    {
        kdcOptionsLength = 0;
        cNameLength = 0;
        realmLength = 0;
        realmBytes = null;
        sNameLength = 0;
        fromLength = 0;
        tillLength = 0;
        rtimeLength = 0;
        nonceLength = 0;
        eTypeLength = 0;
        eTypeSeqLength = 0;
        eTypeLengths = null;
        addressesLength = 0;
        encAuthzDataLength = 0;
        additionalTicketLength = 0;
        additionalTicketSeqLength = 0;
        additionalTicketsLengths = null;
        kdcReqBodySeqLength = 0;
        kdcReqBodyLength = 0;
    }


    /**
     * Pretty print the instance
     */
    public String toString( String tabs )
    {
        StringBuilder sb = new StringBuilder();

        if ( ( kdcOptions != null ) && ( kdcOptions.size() > 0 ) )
        {
            sb.append( tabs ).append( "KDCOptions : " ).append( kdcOptions ).append( '\n' );
        }

        if ( cName != null )
        {
            sb.append( tabs ).append( "cname : " ).append( cName ).append( '\n' );
        }

        sb.append( tabs ).append( "realm : " ).append( realm ).append( '\n' );

        if ( sName != null )
        {
            sb.append( tabs ).append( "sname : " ).append( sName ).append( '\n' );
        }

        if ( from != null )
        {
            sb.append( tabs ).append( "from : " ).append( from ).append( '\n' );
        }

        sb.append( tabs ).append( "till : " ).append( till ).append( '\n' );

        if ( rtime != null )
        {
            sb.append( tabs ).append( "rtime : " ).append( rtime ).append( '\n' );
        }

        sb.append( tabs ).append( "nonce : " ).append( nonce ).append( '\n' );

        sb.append( tabs ).append( "etype : " );
        boolean isFirst = true;

        for ( EncryptionType encryptionType : eType )
        {
            if ( isFirst )
            {
                isFirst = false;
            }
            else
            {
                sb.append( " " );
            }

            sb.append( encryptionType );
        }

        if ( addresses != null )
        {
            sb.append( '\n' );
            sb.append( tabs ).append( "addresses : " );
            isFirst = true;

            for ( HostAddress hostAddress : addresses.getAddresses() )
            {
                if ( isFirst )
                {
                    isFirst = false;
                }
                else
                {
                    sb.append( " " );
                }

                sb.append( hostAddress );
            }
        }

        if ( encAuthorizationData != null )
        {
            sb.append( '\n' );
            sb.append( tabs ).append( "enc-authorization-data" ).append( encAuthorizationData );
        }

        if ( !additionalTickets.isEmpty() )
        {
            sb.append( '\n' );
            sb.append( tabs ).append( "Tickets : " );
            isFirst = true;

            for ( Ticket ticket : additionalTickets )
            {
                if ( isFirst )
                {
                    isFirst = false;
                    sb.append( '\n' );
                }

                sb.append( ticket.toString( tabs + "    " ) );
            }
        }

        return sb.toString();
    }


    /**
     * @see Object#toString()
     */
    public String toString()
    {
        return toString( "" );
    }
}
