Skip to content
Snippets Groups Projects
c14.h 16.2 KiB
Newer Older
Valerio Pastore's avatar
Valerio Pastore committed
/**
 * 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.
 */

#pragma once

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

#include <Base_Packet.h>

namespace C14 {

static const int NUM_PDM = 37;
static const int LOW_GAINS_SIZE = 64;
static const int HIGH_GAINS_SIZE = 64;
static const int TIME_TRIGGERS_SIZE = 64;


Valerio Pastore's avatar
Valerio Pastore committed
struct PDMBlock {
    bool pdmVal;
    bool trgEnb;
    bool trgPdm;
    bool evtVal;
    int32_t spare_3;
    int32_t pdmID;
    std::vector<int32_t > highgains;
    std::vector<int32_t > lowgains;
    std::vector<int32_t > timeTriggers;
    int64_t hitRegister;
    int64_t triggerMask;
    int32_t sipmTemp1;
    int32_t sipmTemp2;
    int32_t sipmTemp3;
    int32_t sipmHighVoltage;
    int32_t sipmCurrent;
    PDMBlock() :
        pdmVal(bool()),
        trgEnb(bool()),
        trgPdm(bool()),
        evtVal(bool()),
        spare_3(int32_t()),
        pdmID(int32_t()),
        highgains(std::vector<int32_t >()),
        lowgains(std::vector<int32_t >()),
        timeTriggers(std::vector<int32_t >()),
        hitRegister(int64_t()),
        triggerMask(int64_t()),
        sipmTemp1(int32_t()),
        sipmTemp2(int32_t()),
        sipmTemp3(int32_t()),
        sipmHighVoltage(int32_t()),
        sipmCurrent(int32_t())
        { }
};

struct C14 {
    int32_t telescopeID;
    int32_t type;
    int32_t subType;
    int32_t ssc;
    int32_t packetLength;
    int32_t year;
    int32_t month;
    int32_t day;
    int32_t hours;
    int32_t minutes;
    int32_t seconds;
    bool validTime;
    int32_t timeTagNanosec;
    int32_t eventCounter;
    bool lid;
    bool fibSt;
    bool fibCont;
    bool fibPuls;
    int32_t rgbCont;
    int32_t rgbPuls;
    int32_t spare_0;
    int32_t pixelTriggerDiscriminatorThreshold;
    int32_t pixelTriggerChargeDiscriminatorThreshold;
    bool ptm;
    int32_t triggerPixelId;
    int32_t triggerType;
    int32_t triggerConfig;
    int32_t spare_1;
    int32_t extTriggerType;
    int32_t extTriggerFrequency;
    int32_t spare_2;
    std::vector<PDMBlock > PDMs;
    C14() :
        telescopeID(int32_t()),
        type(int32_t()),
        subType(int32_t()),
        ssc(int32_t()),
        packetLength(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()),
        eventCounter(int32_t()),
        lid(bool()),
        fibSt(bool()),
        fibCont(bool()),
        fibPuls(bool()),
        rgbCont(int32_t()),
        rgbPuls(int32_t()),
        spare_0(int32_t()),
        pixelTriggerDiscriminatorThreshold(int32_t()),
        pixelTriggerChargeDiscriminatorThreshold(int32_t()),
        ptm(bool()),
        triggerPixelId(int32_t()),
        triggerType(int32_t()),
        triggerConfig(int32_t()),
        spare_1(int32_t()),
        extTriggerType(int32_t()),
        extTriggerFrequency(int32_t()),
        spare_2(int32_t()),
        PDMs(std::vector<PDMBlock >())
        { }
};

}
namespace avro {
template<> struct codec_traits<C14::PDMBlock> {
    static void encode(Encoder& e, const C14::PDMBlock& v) {
        avro::encode(e, v.pdmVal);
        avro::encode(e, v.trgEnb);
        avro::encode(e, v.trgPdm);
        avro::encode(e, v.evtVal);
        avro::encode(e, v.spare_3);
        avro::encode(e, v.pdmID);
        avro::encode(e, v.highgains);
        avro::encode(e, v.lowgains);
        avro::encode(e, v.timeTriggers);
        avro::encode(e, v.hitRegister);
        avro::encode(e, v.triggerMask);
        avro::encode(e, v.sipmTemp1);
        avro::encode(e, v.sipmTemp2);
        avro::encode(e, v.sipmTemp3);
        avro::encode(e, v.sipmHighVoltage);
        avro::encode(e, v.sipmCurrent);
    }
    static void decode(Decoder& d, C14::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.trgEnb);
                    break;
                case 2:
                    avro::decode(d, v.trgPdm);
                    break;
                case 3:
                    avro::decode(d, v.evtVal);
                    break;
                case 4:
                    avro::decode(d, v.spare_3);
                    break;
                case 5:
                    avro::decode(d, v.pdmID);
                    break;
                case 6:
                    avro::decode(d, v.highgains);
                    break;
                case 7:
                    avro::decode(d, v.lowgains);
                    break;
                case 8:
                    avro::decode(d, v.timeTriggers);
                    break;
                case 9:
                    avro::decode(d, v.hitRegister);
                    break;
                case 10:
                    avro::decode(d, v.triggerMask);
                    break;
                case 11:
                    avro::decode(d, v.sipmTemp1);
                    break;
                case 12:
                    avro::decode(d, v.sipmTemp2);
                    break;
                case 13:
                    avro::decode(d, v.sipmTemp3);
                    break;
                case 14:
                    avro::decode(d, v.sipmHighVoltage);
                    break;
                case 15:
                    avro::decode(d, v.sipmCurrent);
                    break;
                default:
                    break;
                }
            }
        } else {
            avro::decode(d, v.pdmVal);
            avro::decode(d, v.trgEnb);
            avro::decode(d, v.trgPdm);
            avro::decode(d, v.evtVal);
            avro::decode(d, v.spare_3);
            avro::decode(d, v.pdmID);
            avro::decode(d, v.highgains);
            avro::decode(d, v.lowgains);
            avro::decode(d, v.timeTriggers);
            avro::decode(d, v.hitRegister);
            avro::decode(d, v.triggerMask);
            avro::decode(d, v.sipmTemp1);
            avro::decode(d, v.sipmTemp2);
            avro::decode(d, v.sipmTemp3);
            avro::decode(d, v.sipmHighVoltage);
            avro::decode(d, v.sipmCurrent);
        }
    }
};

template<> struct codec_traits<C14::C14> {
    static void encode(Encoder& e, const C14::C14& 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.packetLength);
        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.eventCounter);
        avro::encode(e, v.lid);
        avro::encode(e, v.fibSt);
        avro::encode(e, v.fibCont);
        avro::encode(e, v.fibPuls);
        avro::encode(e, v.rgbCont);
        avro::encode(e, v.rgbPuls);
        avro::encode(e, v.spare_0);
        avro::encode(e, v.pixelTriggerDiscriminatorThreshold);
        avro::encode(e, v.pixelTriggerChargeDiscriminatorThreshold);
        avro::encode(e, v.ptm);
        avro::encode(e, v.triggerPixelId);
        avro::encode(e, v.triggerType);
        avro::encode(e, v.triggerConfig);
        avro::encode(e, v.spare_1);
        avro::encode(e, v.extTriggerType);
        avro::encode(e, v.extTriggerFrequency);
        avro::encode(e, v.spare_2);
        avro::encode(e, v.PDMs);
    }
    static void decode(Decoder& d, C14::C14& 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.packetLength);
                    break;
                case 5:
                    avro::decode(d, v.year);
                    break;
                case 6:
                    avro::decode(d, v.month);
                    break;
                case 7:
                    avro::decode(d, v.day);
                    break;
                case 8:
                    avro::decode(d, v.hours);
                    break;
                case 9:
                    avro::decode(d, v.minutes);
                    break;
                case 10:
                    avro::decode(d, v.seconds);
                    break;
                case 11:
                    avro::decode(d, v.validTime);
                    break;
                case 12:
                    avro::decode(d, v.timeTagNanosec);
                    break;
                case 13:
                    avro::decode(d, v.eventCounter);
                    break;
                case 14:
                    avro::decode(d, v.lid);
                    break;
                case 15:
                    avro::decode(d, v.fibSt);
                    break;
                case 16:
                    avro::decode(d, v.fibCont);
                    break;
                case 17:
                    avro::decode(d, v.fibPuls);
                    break;
                case 18:
                    avro::decode(d, v.rgbCont);
                    break;
                case 19:
                    avro::decode(d, v.rgbPuls);
                    break;
                case 20:
                    avro::decode(d, v.spare_0);
                    break;
                case 21:
                    avro::decode(d, v.pixelTriggerDiscriminatorThreshold);
                    break;
                case 22:
                    avro::decode(d, v.pixelTriggerChargeDiscriminatorThreshold);
                    break;
                case 23:
                    avro::decode(d, v.ptm);
                    break;
                case 24:
                    avro::decode(d, v.triggerPixelId);
                    break;
                case 25:
                    avro::decode(d, v.triggerType);
                    break;
                case 26:
                    avro::decode(d, v.triggerConfig);
                    break;
                case 27:
                    avro::decode(d, v.spare_1);
                    break;
                case 28:
                    avro::decode(d, v.extTriggerType);
                    break;
                case 29:
                    avro::decode(d, v.extTriggerFrequency);
                    break;
                case 30:
                    avro::decode(d, v.spare_2);
                    break;
                case 31:
                    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.packetLength);
            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.eventCounter);
            avro::decode(d, v.lid);
            avro::decode(d, v.fibSt);
            avro::decode(d, v.fibCont);
            avro::decode(d, v.fibPuls);
            avro::decode(d, v.rgbCont);
            avro::decode(d, v.rgbPuls);
            avro::decode(d, v.spare_0);
            avro::decode(d, v.pixelTriggerDiscriminatorThreshold);
            avro::decode(d, v.pixelTriggerChargeDiscriminatorThreshold);
            avro::decode(d, v.ptm);
            avro::decode(d, v.triggerPixelId);
            avro::decode(d, v.triggerType);
            avro::decode(d, v.triggerConfig);
            avro::decode(d, v.spare_1);
            avro::decode(d, v.extTriggerType);
            avro::decode(d, v.extTriggerFrequency);
            avro::decode(d, v.spare_2);
            avro::decode(d, v.PDMs);
        }
    }
};

void encodeC14(Encoder &avroencoder,
		inaf::oasbo::PacketLib::BasePacket &packet) {
	// PACKET HEADER
	int offset;
	for (offset = 0; offset < 11; offset++)
		avro::encode(avroencoder, (int32_t) packet[offset].value());

	avro::encode(avroencoder, (bool) packet[11].value());
	avro::encode(avroencoder, (int32_t) packet[12].value());
	avro::encode(avroencoder, (int32_t) packet[13].value());
	avro::encode(avroencoder, (bool) packet[14].value());
	avro::encode(avroencoder, (bool) packet[15].value());
	avro::encode(avroencoder, (bool) packet[16].value());
	avro::encode(avroencoder, (bool) packet[17].value());

	// PACKET DATA FIELD HEADER EXTENSION
	for (offset = 18; offset < 23; offset++)
		avro::encode(avroencoder, (int32_t) packet[offset].value());

	avro::encode(avroencoder, (bool) packet[23].value());
	for (offset = 24; offset < 31; offset++)
		avro::encode(avroencoder, (int32_t) packet[offset].value());

	// PACKET SOURCE DATA FIELD
	avroencoder.arrayStart();
	avroencoder.setItemCount(C14::NUM_PDM);

	for (int i = 0; i < C14::NUM_PDM; i++) {
		avroencoder.startItem();
		avro::encode(avroencoder, (bool) packet[offset++].value());
		avro::encode(avroencoder, (bool) packet[offset++].value());
		avro::encode(avroencoder, (bool) packet[offset++].value());
		avro::encode(avroencoder, (bool) packet[offset++].value());

		avro::encode(avroencoder, (int32_t) packet[offset++].value());
		avro::encode(avroencoder, (int32_t) packet[offset++].value());

		avroencoder.arrayStart();
		avroencoder.setItemCount(C14::HIGH_GAINS_SIZE);
		for(int i = 0; i < C14::HIGH_GAINS_SIZE; i++){
			avroencoder.startItem();
			avro::encode(avroencoder, (int32_t) packet[offset+i].value());
		}
		offset += C14::HIGH_GAINS_SIZE;
		avroencoder.arrayEnd();
		avroencoder.arrayStart();
		avroencoder.setItemCount(C14::LOW_GAINS_SIZE);
		for(int i = 0; i < C14::LOW_GAINS_SIZE; i++){
			avroencoder.startItem();
			avro::encode(avroencoder, (int32_t) packet[offset+i].value());
		}
		offset += C14::LOW_GAINS_SIZE;
		avroencoder.arrayEnd();
		avroencoder.arrayStart();
		avroencoder.setItemCount(C14::TIME_TRIGGERS_SIZE);
		for(int i = 0; i < C14::TIME_TRIGGERS_SIZE; i++){
			avroencoder.startItem();
			avro::encode(avroencoder, (int32_t) packet[offset+i].value());
		}
		offset += C14::TIME_TRIGGERS_SIZE;
		avroencoder.arrayEnd();
		avro::encode(avroencoder, (long) packet[offset++].value());
		avro::encode(avroencoder, (long) packet[offset++].value());
		avro::encode(avroencoder, (int32_t) packet[offset++].value());
		avro::encode(avroencoder, (int32_t) packet[offset++].value());
		avro::encode(avroencoder, (int32_t) packet[offset++].value());
		avro::encode(avroencoder, (int32_t) packet[offset++].value());
		avro::encode(avroencoder, (int32_t) packet[offset++].value());
	}
	avroencoder.arrayEnd();
}