/**
 * 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.
 */

/*
 * XSEC
 *
 * XSECCryptoSymmetricKey := Bulk encryption algorithms should all be
 *                          implemented via this interface
 *
 * Author(s): Berin Lautenbach
 *
 * $Id$
 *
 */



#ifndef OPENSSLCRYPTOSYMMETRICKEY_INCLUDE
#define OPENSSLCRYPTOSYMMETRICKEY_INCLUDE

#include <xsec/framework/XSECDefs.hpp>
#include <xsec/enc/XSECCryptoSymmetricKey.hpp>

#if defined (XSEC_HAVE_OPENSSL)

// OpenSSL Includes

#include <openssl/evp.h>

#define MAX_BLOCK_SIZE      32

/**
 * \ingroup opensslcrypto
 */

/**
 * \brief Base interface definition for symmetric key material.
 *
 * This is the implementation for a wrapper of OpenSSL symmetric
 * crypto functions.
 */

class XSEC_EXPORT OpenSSLCryptoSymmetricKey : public XSECCryptoSymmetricKey {

public :

    /** @name Constructors and Destructors */
    //@{
    
    /**
     * \brief Constructor
     *
     * Can only construct a Symmetric key if we know what type it is
     **/

    OpenSSLCryptoSymmetricKey(XSECCryptoSymmetricKey::SymmetricKeyType type);

    /**
     * \brief Destructor 
     *
     * Implementations must ensure that the held key is properly destroyed
     * (overwritten) when key objects are deleted.
     */

    virtual ~OpenSSLCryptoSymmetricKey();

    //@}

    /** @name Basic CryptoKey Interface methods */
    //@{

    /**
     * \brief Returns a string that identifies the crypto owner of this library.
     */

    virtual const XMLCh * getProviderName() const;

    /**
     * \brief Clone the key
     *
     * All keys need to be able to copy themselves and return
     * a pointer to the copy.  This allows the library to 
     * duplicate keys.
     */

    virtual XSECCryptoKey * clone() const;

    //@}

    /** @name Symmetric key interface methods */
    //@{

    /**
     * \brief What type of symmetric key is this?
     *
     * There are a number of different types of symmetric key.
     * This method allows callers to determine the type of this
     * particular key
     */

    SymmetricKeyType getSymmetricKeyType(void) const;

    /**
     * \brief Set the key from the provided bytes
     *
     * Symmetric keys can all be loaded from a buffer containing a series
     * of bytes.
     *
     * @param key The buffer containing the key bytes
     * @param keyLen The number of key bytes in the buffer
     *
     */

    void setKey(const unsigned char * key, unsigned int keyLen);

    /**
     * \brief Initialise an decryption process
     *
     * Setup the key to get ready for a decryption session.
     * Callers can pass in an IV.  If one is not provided, 
     * but the algorithm requires one (e.g. 3DES_CBC), then 
     * implementations should assume that the start of the
     * cipher text stream will in fact be the IV.
     *
     * @param doPad By default, we perform padding for last block
     * @param mode mode selection (Currently ECB or CBC mode only)
     * @param iv Initialisation Vector to be used.  NULL if one is
     * not required, or if IV will be set from data stream
     * @param tag Authentication tag to be used for AEAD ciphers
     * @param taglen length of Authentication Tag
     * @returns true if the initialisation succeeded.
     */

    virtual bool decryptInit(bool doPad = true,
                             SymmetricKeyMode mode = MODE_CBC,
                             const unsigned char * iv = NULL,
                             const unsigned char* tag = NULL,
                             unsigned int taglen = 0);

    /**
     * \brief Continue an decrypt operation using this key.
     *
     * Decryption must have been set up using an encryptInit
     * call.  Takes the inBuf and continues a decryption operation,
     * writing the output to outBuf.
     *
     * This function does not have to guarantee that all input
     * will be decrypted.  In cases where the input is not a length
     * of the block size, the implementation will need to hold back
     * cipher-text to be handles during the next operation.
     *
     * @note While maxOutLength is defined, the OpenSSL libraries will
     * not read the value, so the onus is on the caller to ensure the
     * buffer is long enough to hold the output!
     *
     * @param inBuf Octets to be decrypted
     * @param plainBuf Buffer to place output in
     * @param inLength Number of bytes to decrypt
     * @param maxOutLength Maximum number of bytes to place in output 
     * buffer
     * @returns Bytes placed in output Buffer
     */

    virtual unsigned int decrypt(const unsigned char * inBuf, 
                                 unsigned char * plainBuf, 
                                 unsigned int inLength,
                                 unsigned int maxOutLength);

    /**
     * \brief Finish a decryption operation
     *
     * Complete a decryption process.  No cipher text is passed in,
     * as this should simply be removing any remaining text from
     * the plain storage buffer.
     *
     * May throw an exception if there is some stored cipher text
     * that is not the length of the block size for block algorithms.
     *
     * @note While maxOutLength is defined, the OpenSSL libraries will
     * not read the value, so the onus is on the caller to ensure the
     * buffer is long enough to hold the output!
     *
     * @param plainBuf Buffer to place any remaining plain text in
     * @param maxOutLength Maximum number of bytes to pace in output
     * @returns Bytes placed in output buffer
     */

    virtual unsigned int decryptFinish(unsigned char * plainBuf,
                                       unsigned int maxOutLength);

    /**
     * \brief Initialise an encryption process
     *
     * Setup the key to get ready for a decryption session.
     * Callers can pass in an IV.  If one is not provided, 
     * but the algorithm requires one (e.g. 3DES_CBC), then
     * implementations are required to generate one.
     *
     * @param doPad By default, we perform padding for last block
     * @param mode What mode to handle blocks (Currently CBC or ECB)
     * @param iv Initialisation Vector to be used.  NULL if one is
     * not required, or if IV is to be generated
     * @returns true if the initialisation succeeded.
     */

    virtual bool encryptInit(bool doPad = true, 
                             SymmetricKeyMode mode = MODE_CBC,
                             const unsigned char * iv = NULL);

    /**
     * \brief Continue an encryption operation using this key.
     *
     * Encryption must have been set up using an encryptInit
     * call.  Takes the inBuf and continues a encryption operation,
     * writing the output to outBuf.
     *
     * This function does not have to guarantee that all input
     * will be encrypted.  In cases where the input is not a length
     * of the block size, the implementation will need to hold back
     * plain-text to be handled during the next operation.
     *
     * @param inBuf Octets to be encrypted
     * @param cipherBuf Buffer to place output in
     * @param inLength Number of bytes to encrypt
     * @param maxOutLength Maximum number of bytes to place in output 
     * buffer
     * @returns Bytes placed in output Buffer
     */

    virtual unsigned int encrypt(const unsigned char * inBuf, 
                                 unsigned char * cipherBuf, 
                                 unsigned int inLength,
                                 unsigned int maxOutLength);

    /**
     * \brief Finish a encryption operation
     *
     * Complete a encryption process.  No plain text is passed in,
     * as this should simply be removing any remaining text from
     * the plain storage buffer and creating a final padded block.
     *
     * Padding is performed by taking the remaining block, and
     * setting the last byte to equal the number of bytes of
     * padding.  If the plain was an exact multiple of the block size,
     * then an extra block of padding will be used.  For example, if 
     * the block size is 8 bytes, and there were three remaining plain
     * text bytes (0x01, 0x02 and 0x03), the final block will be :
     *
     * 0x010203????????05
     *
     * @param plainBuf Buffer to place final block of cipher text in
     * @param maxOutLength Maximum number of bytes to pace in output
     * @param taglen length of Authentication Tag
     * @returns Bytes placed in output buffer
     */

    virtual unsigned int encryptFinish(unsigned char * plainBuf,
                                       unsigned int maxOutLength,
                                       unsigned int taglen = 0);

    //@}

    /** @name OpenSSL Library Specific functions */
    //@{

    /**
     * \brief Get OpenSSL cipher context structure
     */

    EVP_CIPHER_CTX * getOpenSSLEVP_CIPHER_CTX(void) {return mp_ctx;}

    /**
     * \brief Get OpenSSL cipher context structure
     */

    const EVP_CIPHER_CTX * getOpenSSLEVP_CIPHER_CTX(void) const {return mp_ctx;}

    //@}

private:

    // Unimplemented constructors
    
    OpenSSLCryptoSymmetricKey();
    OpenSSLCryptoSymmetricKey(const OpenSSLCryptoSymmetricKey &);
    OpenSSLCryptoSymmetricKey & operator= (const OpenSSLCryptoSymmetricKey &);

    // Private functions
    int decryptCtxInit(const unsigned char* iv, const unsigned char* tag, unsigned int taglen);

    // Private variables
    SymmetricKeyType                m_keyType;
    SymmetricKeyMode                m_keyMode;
    EVP_CIPHER_CTX                  *mp_ctx;        // OpenSSL Cipher Context structure
#if (OPENSSL_VERSION_NUMBER < 0x10100000L)
    EVP_CIPHER_CTX                  m_ctx_space;    // OpenSSL Cipher Context structure - store
#endif
    safeBuffer                      m_keyBuf;       // Holder of the key
    safeBuffer                      m_tagBuf;       // Holder of authentication tag
    unsigned int                    m_keyLen;
    bool                            m_initialised;  // Is the context ready to work?
    unsigned char                   m_lastBlock[MAX_BLOCK_SIZE];
    int                             m_blockSize;
    int                             m_ivSize;
    int                             m_bytesInLastBlock;
    bool                            m_ivSent;       // Has the IV been put in the stream
    bool                            m_doPad;        // Do we pad last block?
};

#endif /* XSEC_HAVE_OPENSSL */
#endif /* OPENSSLCRYPTOSYMMETRICKEY_INCLUDE */
