
// Implementation of the EventTrkReader class.

#include "ReaderAlgorithms.h"

extern "C" {
    //Passo il path verso la il file temporaneo
    extern void trkeventpkt_(int*, unsigned char[], long int*, int*);
    //Struct per il passaggio di dati da e verso la chiamata fortran
    extern struct {
	int DAQmode[12];
	int DSPnumber[12];
	int DATAlength[12];
	int eventn[12];
	int nclust[12];
	int cutc[12];
	int cutcl[12];
	int addrcluster[3][12];
	int signcluster[3][12];
	int fc[12];
	int compressiontime[12];
	int fl5[12];
	int fl4[12];
	int fl3[12];
	int fl2[12];
	int fl1[12];
	int fl6[12];
	int checksum[12];
	int TOTDATAlength;
	int datatracker[49152];
	int pnum[12];
	int cmdnum[12];
	int bid[12];
	int alarm[12];
	int aswr[12];
	int good0;          
	int crc[12];        
    } level0_; 
#include <dirent.h>
}

using namespace pamela;
using namespace pamela::techmodel;

/**
 * Constructor. 
 */
EventTrkReader::EventTrkReader(void): 
  TechmodelAlgorithm(PacketType::EventTrk, "TechmodelEventTrkReader") { 
  eventTrk = new EventTrkEvent();
}

/**
 * Get a string with the version info of the algorithm.
 */
std::string EventTrkReader::GetVersionInfo(void) const {
  return 
    "$Trailer: /home/cvsmanager/yoda/techmodel/EventTrkReader.cpp,v 1.1.1.1 2004/07/06 12:20:23 kusanagi Exp $\n";
}

/**
 * Initialize the algorithm with a special run. This will initialize the
 * event reader routines for all packet types.
 */
void EventTrkReader::Init(PamelaRun *run) {
  run->WriteSubPacket(this, &eventTrk, eventTrk->Class());
}

/**
 * Unpack the EventTrk event from an input file.
 */
void EventTrkReader::PKT_RunEvent(char* subData, long int length) throw (Exception){
    int       ERROR=0;
    stringstream oss;	
    string msg;    

    int curpos=1;
    
    //Call to the FORTRAN routin that unpack tracker events
    trkeventpkt_( &ERROR,(unsigned char*)subData, &length, &curpos); 

   if (ERROR != 0) {
        char *errmsg;
        switch (ERROR){
            case 1: errmsg = "GENERIC TRACKER ERROR";
            break;
            default: errmsg = "TRACKER ERRROR CODE UNIDENTIFIED";
        }
        oss.str("");
        oss << "EventTrk: Fortran77 function trkeventpkt: " <<  errmsg;
      msg=oss.str();
      PamOffLineSW::mainLogUtil->logWarning(msg);	
        
    }
    //Store the unpacked data
    eventTrk->unpackError    = ERROR;
    eventTrk->good0          = level0_.good0;
    memcpy(eventTrk->DAQmode,    level0_.DAQmode,    sizeof(eventTrk->DAQmode));
    memcpy(eventTrk->DSPnumber,  level0_.DSPnumber,  sizeof(eventTrk->DSPnumber));
    memcpy(eventTrk->DATAlength, level0_.DATAlength, sizeof(eventTrk->DATAlength));
    memcpy(eventTrk->eventn,     level0_.eventn,     sizeof(eventTrk->eventn));
    memcpy(eventTrk->nclust,     level0_.nclust,     sizeof(eventTrk->nclust));
    memcpy(eventTrk->cutc,       level0_.cutc,       sizeof(eventTrk->cutc));
    memcpy(eventTrk->cutcl,      level0_.cutcl,      sizeof(eventTrk->cutcl));
//--------have to invert array because of FORTRAN <-> C different management of the indexes
    int tempAddr[3][12];
    int tempSign[3][12];
    memcpy(tempAddr, (level0_.addrcluster), sizeof(tempAddr));
    memcpy(tempSign, (level0_.signcluster), sizeof(tempSign));
    for (int j = 0; j < 12; j++){
        for (int i = 0; i < 3; i++){
            eventTrk->addrcluster[j][i] = tempAddr[i][j];
            eventTrk->signcluster[j][i] = tempSign[i][j];
        }
    }
//-----------------------------------------------------------------------------------------
    
    memcpy(eventTrk->fc,                 level0_.fc,              sizeof(eventTrk->fc));
    memcpy(eventTrk->compressiontime,    level0_.compressiontime, sizeof(eventTrk->compressiontime));
    memcpy(eventTrk->fl1,                level0_.fl1,             sizeof(eventTrk->fl1));
    memcpy(eventTrk->fl2,                level0_.fl2,             sizeof(eventTrk->fl2));
    memcpy(eventTrk->fl3,                level0_.fl3,             sizeof(eventTrk->fl3));
    memcpy(eventTrk->fl4,                level0_.fl4,             sizeof(eventTrk->fl4));
    memcpy(eventTrk->fl5,                level0_.fl5,             sizeof(eventTrk->fl5));
    memcpy(eventTrk->fl6,                level0_.fl6,             sizeof(eventTrk->fl6));
    memcpy(eventTrk->checksum,           level0_.checksum,        sizeof(eventTrk->checksum));
    memcpy(eventTrk->pnum,               level0_.pnum,            sizeof(eventTrk->pnum));
    memcpy(eventTrk->cmdnum,             level0_.cmdnum,          sizeof(eventTrk->cmdnum));    
    memcpy(eventTrk->bid,                level0_.bid,             sizeof(eventTrk->bid));    
    memcpy(eventTrk->alarm,              level0_.alarm,           sizeof(eventTrk->alarm));    
    memcpy(eventTrk->aswr,               level0_.aswr,            sizeof(eventTrk->aswr));          
    memcpy(eventTrk->crc,                level0_.crc,             sizeof(eventTrk->crc));          
    
    eventTrk->TOTDATAlength = level0_.TOTDATAlength;
    eventTrk->TrackerData   = TArrayI(level0_.TOTDATAlength, level0_.datatracker);
}
