/* -*-  Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
/*
 * Copyright (c) 2011 University of California, Los Angeles
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License version 2 as
 * published by the Free Software Foundation;
 *
 * This program 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 for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 *
 * Author: Ilya Moiseenko <iliamo@cs.ucla.edu>
 */

#ifndef _INTEREST_PACKET_H_
#define _INTEREST_PACKET_H_

//#define CCN_INTEREST_LIFETIME_SEC 4
//#define CCN_INTEREST_LIFETIME_MICROSEC (CCN_INTEREST_LIFETIME_SEC * 1000000)

#include <ns3/integer.h>
#include <ns3/header.h>
#include <ns3/packet.h>

#include <string>
#include <vector>
#include <list>

#include "name-components.h"

namespace ns3
{
namespace NDNabstraction
{

/**
 * CCNx XML definition of Interest
 * 
 * Only few important fields are actually implemented in the simulation
 *
 * <xs:element name="Interest" type="InterestType"/>
 * <xs:complexType name="InterestType">
 *   <xs:sequence>
 *     <xs:element name="Name" type="NameType"/>
 *     <xs:element name="MinSuffixComponents" type="xs:nonNegativeInteger"
 *                         minOccurs="0" maxOccurs="1"/>
 *     <xs:element name="MaxSuffixComponents" type="xs:nonNegativeInteger"
 *                         minOccurs="0" maxOccurs="1"/>
 *     <xs:choice minOccurs="0" maxOccurs="1">
 *         <xs:element name="PublisherPublicKeyDigest" type="DigestType"/>
 *         <xs:element name="PublisherCertificateDigest" type="DigestType"/>
 *         <xs:element name="PublisherIssuerKeyDigest" type="DigestType"/>
 *         <xs:element name="PublisherIssuerCertificateDigest" type="DigestType"/>
 *     </xs:choice>
 *     <xs:element name="Exclude" type="ExcludeType"
 *                         minOccurs="0" maxOccurs="1"/>
 *     <xs:element name="ChildSelector" type="xs:nonNegativeInteger"
 *                         minOccurs="0" maxOccurs="1"/>
 *     <xs:element name="AnswerOriginKind" type="xs:nonNegativeInteger"
 *                         minOccurs="0" maxOccurs="1"/>
 *     <xs:element name="Scope" type="xs:nonNegativeInteger"
 * 			minOccurs="0" maxOccurs="1"/>
 *     <xs:element name="InterestLifetime" type="FinegrainLifetimeType"
 * 			minOccurs="0" maxOccurs="1"/>
 *     <xs:element name="Nonce" type="Base64BinaryType"
 * 			minOccurs="0" maxOccurs="1"/>
 *   </xs:sequence>
 * </xs:complexType>
 *
 * <xs:complexType name="NameType">
 *   <xs:sequence>
 *     <xs:element name="Component" type="Base64BinaryType"
 *                 minOccurs="0" maxOccurs="unbounded"/>
 *   </xs:sequence>
 * </xs:complexType>
 * 
 * <xs:complexType name="ExcludeType">
 *   <xs:sequence>
 *     <xs:choice minOccurs="0" maxOccurs="1">
 *         <xs:element name="Any" type="EmptyType"/>
 *         <xs:element name="Bloom" type="Base64BinaryType"/> <!-- Bloom is deprecated --!>
 *     </xs:choice>
 *      <xs:sequence minOccurs="0" maxOccurs="unbounded">
 *         <xs:element name="Component" type="Base64BinaryType"/>
 *         <xs:choice minOccurs="0" maxOccurs="1">
 *             <xs:element name="Any" type="EmptyType"/>
 *             <xs:element name="Bloom" type="Base64BinaryType"/> <!-- Bloom is deprecated --!>
 *         </xs:choice>
 *      </xs:sequence>
 *   </xs:sequence>
 * </xs:complexType>
 * 
 * <!-- Binary representation of time, Unix time epoch, units 2**-12 sec (0.000244140625 sec) -->
 * <!-- The length limit limit of 6 bytes is not actually to be enforced, but
 *      it will be a loooooooong time before anyone cares. --> 
 * 
 * <!-- Binary representation of relative time, relative to "now" -->
 * <xs:complexType name="FinegrainLifetimeType">
 *   <xs:simpleContent>
 *     <xs:extension base="BinaryTime12">
 *       <xs:attribute name="ccnbencoding" type="xs:string" fixed="base64Binary"/>
 *     </xs:extension>
 *   </xs:simpleContent>
 * </xs:complexType>
 *
 * <xs:simpleType name="BinaryTime12">
 *     <xs:restriction base="xs:base64Binary">
 *       <xs:length value="6" fixed="true"/>
 *     </xs:restriction>
 * </xs:simpleType>
 *
 **/

  /**
     NDN InterestPacket and routes to serialize/deserialize

     Simplifications:
     - Name:  binary name components are not supported
     - MinSuffixComponents and MasSuffixComponents: if value is negative (default), will not be serialized
     - ChildSelector, AnswerOriginKind: 0 - false, 1 - true, -1 not set
     - Publisher* elements are not supported
     - Exclude: only simple name matching is supported (Bloom support has been deprecated in CCNx)
     - InterestLifetime: not used if negative
     - Nonce: 32 bit random integer.  If value is 0, will not be serialized
   */
  class InterestHeader : public Header
  {
  public:
    /**
     * Constructor
     *
     * Creates a null header
     **/
    InterestHeader ();

    /**
     * \brief Set interest name
     *
     * Sets name of the interest. For example, SetName( Name::Components("prefix")("postfix") );
     **/
    void
    SetName (const Ptr<Name::Components> &name);

    const Name::Components&
    GetName () const;

    void
    SetMinSuffixComponents (int32_t value);

    int32_t
    GetMinSuffixComponents () const;

    void
    SetMaxSuffixComponents (int32_t value);

    int32_t
    GetMaxSuffixComponents () const;

    /**
     * \brief Set exclude filer
     *
     * For example, SetExclude (Name::Components("exclude1")("exclude2")("exclude3"))
     **/
    void
    SetExclude (const Ptr<Name::Components> &exclude);

    const Name::Components&
    GetExclude () const;

    void
    EnableChildSelector ();

    bool
    IsEnabledChildSelector () const;

    void
    EnableAnswerOriginKind ();

    bool
    IsEnabledAnswerOriginKind () const;

    void
    SetScope (int8_t scope);

    int8_t
    GetScope () const;

    void
    SetInterestLifetime (intmax_t lifetime);

    intmax_t
    GetInterestLifetime () const;

    void
    SetNonce (uint32_t nonce);

    uint32_t
    GetNonce () const;

    //////////////////////////////////////////////////////////////////
    
    static TypeId GetTypeId (void);
    virtual TypeId GetInstanceTypeId (void) const;
    virtual void Print (std::ostream &os) const;
    virtual uint32_t GetSerializedSize (void) const;
    virtual void Serialize (Buffer::Iterator start) const;
    virtual uint32_t Deserialize (Buffer::Iterator start);

  private:
    Ptr<Name::Components> m_name;
    int32_t m_minSuffixComponents; ///< minimum suffix components. not used if negative
    int32_t m_maxSuffixComponents; ///< maximum suffix components. not used if negative
    Ptr<Name::Components> m_exclude; ///< exclude filter
    bool m_childSelector;    
    bool m_answerOriginKind; 
    int8_t m_scope;            ///< -1 not set, 0 local scope, 1 this host, 2 immediate neighborhood
    intmax_t m_interestLifetime; ///< InterestLifetime in 2^{-12} (0.000244140625 sec). not used if negative
    uint32_t m_nonce; ///< Nonce. not used if zero
  };


  // Not sure that we need a separate NndPacket class. Everything useful will be inside (Interest|ContentObject)Header
// class NdnPacket : public Packet 
// {
// public:
//   NdnPacket( )
    // ; 
  // InterestPacket (const unsigned char *name, uint32_t size);
  
          
  // uint32_t GetName (unsigned char *name);
      
  // void AddTimeout (uint32_t milliseconds);
  // uint32_t GetTimeout (void);
  // void RemoveTimeout (void);
      
  // void AddNonce (uint32_t nonce);
  // uint32_t GetNonce (void);
  // void RemoveNonce (void);
      
  // uint32_t maxNameLength;
  
// };
  
}
}

#endif // _NDN_PACKET_H_
