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


#ifndef VAR102PACKET_H_2421229405__H_
#define VAR102PACKET_H_2421229405__H_


#include <sstream>
#include "boost/any.hpp"
#include "Specific.hh"
#include "Encoder.hh"
#include "Decoder.hh"

namespace VAR102 {
struct PDMBlock {
    bool pdmVal;
    int32_t samplingPar;
    int32_t pdmID;
    std::vector<int32_t > variance;
    PDMBlock() :
        pdmVal(bool()),
        samplingPar(int32_t()),
        pdmID(int32_t()),
        variance(std::vector<int32_t >())
        { }
};

struct VAR102 {
    int32_t telescopeID;
    int32_t type;
    int32_t subType;
    int32_t ssc;
    int32_t year;
    int32_t month;
    int32_t day;
    int32_t hours;
    int32_t minutes;
    int32_t seconds;
    bool validTime;
    int32_t timeTagNanosec;
    std::vector<PDMBlock > PDMs;
    VAR102() :
        telescopeID(int32_t()),
        type(int32_t()),
        subType(int32_t()),
        ssc(int32_t()),
        year(int32_t()),
        month(int32_t()),
        day(int32_t()),
        hours(int32_t()),
        minutes(int32_t()),
        seconds(int32_t()),
        validTime(bool()),
        timeTagNanosec(int32_t()),
        PDMs(std::vector<PDMBlock >())
        { }
};

}
namespace avro {
template<> struct codec_traits<VAR102::PDMBlock> {
    static void encode(Encoder& e, const VAR102::PDMBlock& v) {
        avro::encode(e, v.pdmVal);
        avro::encode(e, v.samplingPar);
        avro::encode(e, v.pdmID);
        avro::encode(e, v.variance);
    }
    static void decode(Decoder& d, VAR102::PDMBlock& v) {
        if (avro::ResolvingDecoder *rd =
            dynamic_cast<avro::ResolvingDecoder *>(&d)) {
            const std::vector<size_t> fo = rd->fieldOrder();
            for (std::vector<size_t>::const_iterator it = fo.begin();
                it != fo.end(); ++it) {
                switch (*it) {
                case 0:
                    avro::decode(d, v.pdmVal);
                    break;
                case 1:
                    avro::decode(d, v.samplingPar);
                    break;
                case 2:
                    avro::decode(d, v.pdmID);
                    break;
                case 3:
                    avro::decode(d, v.variance);
                    break;
                default:
                    break;
                }
            }
        } else {
            avro::decode(d, v.pdmVal);
            avro::decode(d, v.samplingPar);
            avro::decode(d, v.pdmID);
            avro::decode(d, v.variance);
        }
    }
};

template<> struct codec_traits<VAR102::VAR102> {
    static void encode(Encoder& e, const VAR102::VAR102& v) {
        avro::encode(e, v.telescopeID);
        avro::encode(e, v.type);
        avro::encode(e, v.subType);
        avro::encode(e, v.ssc);
        avro::encode(e, v.year);
        avro::encode(e, v.month);
        avro::encode(e, v.day);
        avro::encode(e, v.hours);
        avro::encode(e, v.minutes);
        avro::encode(e, v.seconds);
        avro::encode(e, v.validTime);
        avro::encode(e, v.timeTagNanosec);
        avro::encode(e, v.PDMs);
    }
    static void decode(Decoder& d, VAR102::VAR102& v) {
        if (avro::ResolvingDecoder *rd =
            dynamic_cast<avro::ResolvingDecoder *>(&d)) {
            const std::vector<size_t> fo = rd->fieldOrder();
            for (std::vector<size_t>::const_iterator it = fo.begin();
                it != fo.end(); ++it) {
                switch (*it) {
                case 0:
                    avro::decode(d, v.telescopeID);
                    break;
                case 1:
                    avro::decode(d, v.type);
                    break;
                case 2:
                    avro::decode(d, v.subType);
                    break;
                case 3:
                    avro::decode(d, v.ssc);
                    break;
                case 4:
                    avro::decode(d, v.year);
                    break;
                case 5:
                    avro::decode(d, v.month);
                    break;
                case 6:
                    avro::decode(d, v.day);
                    break;
                case 7:
                    avro::decode(d, v.hours);
                    break;
                case 8:
                    avro::decode(d, v.minutes);
                    break;
                case 9:
                    avro::decode(d, v.seconds);
                    break;
                case 10:
                    avro::decode(d, v.validTime);
                    break;
                case 11:
                    avro::decode(d, v.timeTagNanosec);
                    break;
                case 12:
                    avro::decode(d, v.PDMs);
                    break;
                default:
                    break;
                }
            }
        } else {
            avro::decode(d, v.telescopeID);
            avro::decode(d, v.type);
            avro::decode(d, v.subType);
            avro::decode(d, v.ssc);
            avro::decode(d, v.year);
            avro::decode(d, v.month);
            avro::decode(d, v.day);
            avro::decode(d, v.hours);
            avro::decode(d, v.minutes);
            avro::decode(d, v.seconds);
            avro::decode(d, v.validTime);
            avro::decode(d, v.timeTagNanosec);
            avro::decode(d, v.PDMs);
        }
    }
};

}
#endif
