/*
 * Copyright 2009 Funambol, Inc.
 *
 * Licensed 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.
 */

/* $Id$ */

#pragma once

#include <commontypes.h>
#include <platform.h>
#include <serverexchange/DNSQueryDef.h>

#include <arpa/nameser.h>
#if defined(PLATFORM_MAC)
#include <machine/endian.h>
#include <arpa/nameser_compat.h>
#endif

#ifdef PLATFORM_ANDROID
#include "../../src/android/resolv_declarations.h" // add declarations for resolv infrastructure
#endif

typedef HEADER DNS_QUERY_HEADER;

namespace NS_DM_Client
{

    namespace NS_DNS_Query
    {
        typedef int ret_code_t;
        typedef int opcode_t;

        class Header
        {
        public:
            Header(const DNS_QUERY_HEADER& hdr);

            unsigned id() const;
            bool isResponse() const;
//            opcode_t opcode() const;
            bool isAuthoritative() const;
            bool isTruncated() const;
            bool isRecursionDesired() const;
            bool isRecursionAvailable() const;
            bool dataAuthentic() const;
            bool isCheckDisabled() const;
//            ret_code_t rcode() const;
            unsigned questionCount() const;
            unsigned answerCount() const;
            unsigned nsCount() const;
            unsigned additionalCount() const;

            unsigned size() const;

        private:
            unsigned m_id;          /// Query ID
            bool m_resp;            /// false if query, true if response
            opcode_t m_opcode;      /// Operation code
            bool m_authoritative;   /// Whether the answer is authoritative
            bool m_truncated;       /// Whether the answer was truncated
            bool m_rd;              /// Recursion Desired
            bool m_ra;              /// Recursion Available
            bool m_ad;
            bool m_cd;
            ret_code_t m_rcode;     /// Response Code
            unsigned m_qdcount;
            unsigned m_ancount;
            unsigned m_nscount;
            unsigned m_arcount;

        };


        class DnsQuestion {
        public:
            DnsQuestion();

            bool Set(const unsigned char* data, size_t max_len,
                const unsigned char* msgstart, const unsigned char* msgend);

            const String& GetName() const;
            EnumType GetType() const;
            EnumClass GetClass() const;

            size_t GetLength() const;

        protected:
            String m_qname;
            EnumType m_qtype;
            EnumClass m_qclass;
            size_t m_full_length;

        };


        class DnsSrvRr
        {
        public:
            DnsSrvRr();

            bool Set(const unsigned char* data, size_t max_len,
            const unsigned char* msgstart, const unsigned char* msgend);

            const String& name() const;
            EnumType type() const;
            EnumClass getClass() const;
            uint32_t ttl() const;
            uint16_t length() const;
//            const uint8_t* data() const;

            const String& target() const;
            uint16_t priority() const;
            uint16_t weight() const;
            uint16_t port() const;

            size_t  getLength() const;

        protected:
            String m_name;
            EnumType m_type;
            EnumClass m_class;
            uint32_t m_ttl;
            uint16_t m_length;
//            uint8_t* m_data;
            const unsigned char* m_data_ptr;
            size_t m_full_length;

            uint16_t m_priority;
            uint16_t m_weight;
            uint16_t m_port;
            String m_target;
        };
    }

}

