using namespace std;
#include "htrbbaseunpacker.h"
#include "htrblookup.h"
#include "hdebug.h"
#include "hades.h"
#include "hevent.h"
#include "hldsubevt.h"
#include "heventheader.h"
#include <iostream>
#include <iomanip>
#include <stdlib.h>
ClassImp(HTrbBaseUnpacker)
HTrbBaseUnpacker::HTrbBaseUnpacker(UInt_t id) {
debugFlag=0;
debugFlag1=0;
subEvtId=id;
trbDataVer=0;
quietMode=false;
reportCritical=false;
lookup=0;
clearAll();
}
void HTrbBaseUnpacker::clearAll(void){
for(Int_t i=0; i<128; i++){
for(Int_t k=0; k<10; k++){
trbLeadingTime[i][k] = -1000000;
trbTrailingTime[i][k] = -1000000;
trbADC[i][k]=-1;
}
trbLeadingMult[i]=0;
trbTrailingMult[i]=0;
trbTrailingTotalMult[i]=0;
}
}
Int_t HTrbBaseUnpacker::correctRefTimeCh31(void){
Int_t refCh;
Int_t corrTime;
for(Int_t jj=0; jj<4; jj++){
Int_t jo;
Bool_t flag;
flag=false;
jo=jj*32;
for(Int_t ll=0; ll<32; ll++){
if( trbLeadingMult[jo+ll]>0){ flag=true; break;}
}
if(!flag) continue;
refCh = jo+31;
corrTime = trbLeadingTime[refCh][0];
if(corrTime <= -1000000 ){
if(!quietMode){
Info("correctRefTimeCh31","No Ref Time! TRBid %d TDC %d",subEvtId,jj);
}
corrTime=-1000000;
}
for(Int_t ll=0; ll<32; ll++){
Int_t ii;
ii=jo+ll;
for(Int_t kk=0; kk<10; kk++){
trbLeadingTime[ii][kk] = trbLeadingTime[ii][kk] - corrTime + 40000;
trbTrailingTime[ii][kk] = trbTrailingTime[ii][kk] - corrTime + 40000;
}
}
}
return 0;
}
Int_t HTrbBaseUnpacker::correctRefTimeCh127(void){
Int_t corrTime;
corrTime = trbLeadingTime[127][0];
if(corrTime <= -1000000 ){
if(!quietMode){
Info("correctRefTimeCh127","No Ref Time! TRBid %d",subEvtId);
}
corrTime=-1000000;
}
for(Int_t jj=0; jj<128; jj++){
for(Int_t kk=0; kk<10; kk++){
trbLeadingTime[jj][kk] = trbLeadingTime[jj][kk] - corrTime + 40000;
trbTrailingTime[jj][kk] = trbTrailingTime[jj][kk] - corrTime + 40000;
}
}
return 0;
}
Int_t HTrbBaseUnpacker::correctOverflow(void){
return 0;
}
Bool_t HTrbBaseUnpacker::fill_pair(Int_t ch,Int_t time,Int_t length)
{
if( trbLeadingMult[ch]<10){
trbLeadingTime[ch][trbLeadingMult[ch]]=time;
trbTrailingTime[ch][trbLeadingMult[ch]]=time+length;
}
trbLeadingMult[ch]++;
trbTrailingMult[ch]=trbLeadingMult[ch];
return(trbLeadingMult[ch]<=10);
}
Bool_t HTrbBaseUnpacker::fill_lead(Int_t ch,Int_t time)
{
if( trbLeadingMult[ch]<10){
trbLeadingTime[ch][trbLeadingMult[ch]]=time;
}
trbLeadingMult[ch]++;
return(trbLeadingMult[ch]<=10);
}
Bool_t HTrbBaseUnpacker::fill_trail(Int_t ch,Int_t time)
{
trbTrailingTotalMult[ch]++;
Int_t m;
m=trbLeadingMult[ch];
if(m==0) return kFALSE;
if( m<=10){
if( trbTrailingMult[ch]!=m){
trbTrailingTime[ch][m-1]=time;
trbADC[ch][m-1] = time - trbLeadingTime[ch][m-1];
if(trbADC[ch][m-1]<0){
trbADC[ch][m-1]+=0x80000;
}
}else{
return kFALSE;
}
}
trbTrailingMult[ch]=m;
return(trbTrailingMult[ch]<=10);
}
void HTrbBaseUnpacker::PrintTdcError(UInt_t e, UInt_t subEvntId)
{
const Char_t *e_str[15]={
"Hit lost in group 0 from read-out FIFO overflow",
"Hit lost in group 0 from L1 buffer overflow",
"Hit error have been detected in group 0",
"Hit lost in group 1 from read-out FIFO overflow",
"Hit lost in group 1 from L1 buffer overflow",
"Hit error have been detected in group 1",
"Hit lost in group 2 from read-out FIFO overflow",
"Hit lost in group 2 from L1 buffer overflow",
"Hit error have been detected in group 2",
"Hit lost in group 3 from read-out FIFO overflow",
"Hit lost in group 3 from L1 buffer overflow",
"Hit error have been detected in group 3",
"Hits rejected because of programmed event size limit",
"Event lost (trigger FIFO overflow)",
"Internal fatal chip error has been detected"
};
if(e==0) return;
cout << "=== TRB/TDC Error analysis: TRB id = " <<subEvntId<< endl;
for(Int_t i=0; i<15; i++){
if( e&0x1){
cout << e_str[i] << endl;
}
e>>=1;
}
cout << "===" << endl;
}
Int_t HTrbBaseUnpacker::decode(void)
{
clearAll();
UInt_t nEvt = 0;
Int_t nEvId = 0;
Int_t TdcId;
Int_t nCountTDC = 0;
UInt_t nEvtNr = 0;
UInt_t nSizeCounter = 0;
UInt_t nTdcEvtId = 0;
UInt_t TdcDataLen=0;
UInt_t uBlockSize=0;
UInt_t* data = pSubEvt->getData();
UInt_t* end = pSubEvt->getEnd();
nEvt = gHades->getCurrentEvent()->getHeader()->getEventSeqNumber();
if(debugFlag1 > 0){
gHades->getCurrentEvent()->getHeader()->setId(1);
}
nEvId = gHades->getCurrentEvent()->getHeader()->getId();
if(debugFlag > 0){
cout<<hex<<"data word: "<<*data<<dec<<" --Subevent Header"<<endl;
}
if( ((debugFlag > 0 || DEBUG_LEVEL>4) && (!quietMode))){
printf("=== Unpacker start SubEvtId: %d\n===Header: %X Nr:%d Len:%d\n",subEvtId,*data>>16,nEvtNr,uBlockSize);
}
trbDataVer=0;
trbExtensionSize=0;
trbDataPairFlag=false;
if(((*data >> 24) & 0xFF)!=0xBE) {
nSizeCounter++;
uBlockSize=*data&0xFFFF;
nEvtNr=(*data>>16)&0xFF;
data ++;
nSizeCounter++;
Int_t nData;
trbDataVer = (*data>>24)&0xFF;
trbDataPairFlag = (*data>>16)&0x1;
trbExtensionSize = *data&0x0000FFFF;
if( ((debugFlag > 0 || DEBUG_LEVEL>4) && (!quietMode))){
printf("=== Unpacker NewHeader: %08X Ver:%d Ext:%d Pair:%d\n",*data,trbDataVer,trbExtensionSize,(Int_t)trbDataPairFlag);
}
if(trbExtensionSize != 0){
for(Int_t ext_cycle=0; ext_cycle<trbExtensionSize; ext_cycle++){
data++;
nSizeCounter++;
nData = *data;
if(trbExtensionSize < 128) {
trbDataExtension[ext_cycle] = nData;
}
else{
cout<<"--TRBBASEUNPACKER-SubEventId= "<<subEvtId<<" too many data words, limit is 128"<<endl;
}
}
}
}
else {
if((*data&0xFFFF0000)==0xBE010000){
if(!quietMode)Error("TRB unpack","TRB Buffer overflow, Data truncated. No lethal error, but please report if error is persistend!!!");
return(kFALSE);
}
if((*data&0xFFFF0000)!=0xBEEF0000 && (*data&0xFFFF0000)!=0xBE000000){
if(!quietMode)Error("TRB unpack","NO $BEEF FOUND!!!");
}
uBlockSize=*data&0xFF;
nEvtNr=(*data>>8)&0xFF;
if(nEvtNr!=(UInt_t)pSubEvt->getTrigNr()){
if(!quietMode){
Error("TRB unpack","TRB EvtNr!=pSubEvt->getTrigNr() ********* Event Mixing *********");
printf("=== %d != %d \n",nEvtNr,(UInt_t)pSubEvt->getTrigNr());
}
return(kFALSE);
}
#warning "Change value to 10 if all TRBs have 4 TDCs after beamtime may06"
if(uBlockSize<8){
if(!quietMode)printf("Error in TRB unpack: Suspicious length (too small for header/trailer of tdcs) %d , might be a overflow!\n",uBlockSize);
}
nSizeCounter++;
}
while ( ++data<end && *data!=0x0 )
{
UInt_t dataword;
dataword=*data;
nSizeCounter++;
if(dataword==0xDEADFACE){
if( ((debugFlag > 0 || DEBUG_LEVEL>4) && (!quietMode))){
printf("TRB unpack: Found DEADFACE -> break %08X %08X\n",*data,*end);
}
break;
}
TdcId=(dataword>>24)&0xF;
TdcId=nCountTDC;
if(TdcDataLen>0) TdcDataLen++;
switch(dataword>>28){
case 0:{
if( ((debugFlag > 0 || DEBUG_LEVEL>4) && (!quietMode))){
printf("TRB unpack: Found GLOBAL Header $%08X\n",dataword);
}
if(!quietMode)Info("TRB unpack","Global Header not expected!");
break;
}
case 1:{
if( ((debugFlag > 0 || DEBUG_LEVEL>4) && (!quietMode))){
printf("TRB unpack: Found GLOBAL Trailer $%08X\n",dataword);
}
if(!quietMode)Info("TRB unpack","Global Trailer not expected!");
break;
}
case 2:{
if( ((debugFlag > 0 || DEBUG_LEVEL>4) && (!quietMode))){
printf("TRB unpack: Found TDC %d Header $%04X $%04X\n",TdcId,(dataword>>12)&0xFFF,dataword&0xFFF);
}
if( nCountTDC>0 && nTdcEvtId!=((dataword>>12)&0xFFF)){
if(!quietMode)Error("TRB unpack","TDCs have different EventIds ******* Event Mixing *******");
if(!quietMode)printf("nTdcEvtId: %06X dataword: %06X nEvtNr: %02X\n" , nTdcEvtId ,((dataword>>12)&0xFFF),nEvtNr);
}
if( nEvtNr!=((dataword>>12)&0xFF)){
if(!quietMode)Error("TRB unpack","TDC EventIds != Main EventId ******* Event Mixing *******");
if(!quietMode)printf("nTdcEvtId: %06X dataword: %06X nEvtNr: %02X\n" , nTdcEvtId ,((dataword>>12)&0xFFF),nEvtNr);
}
if( ((debugFlag > 0 || DEBUG_LEVEL>4) && (!quietMode))){
printf("nTdcEvtId: %06X dataword: %06X nEvtNr: %02X\n" , nTdcEvtId ,((dataword>>12)&0xFFF),nEvtNr);
}
nTdcEvtId=(dataword>>12)&0xFFF;
TdcDataLen=1;
break;
}
case 3:{
if( ((debugFlag > 0 || DEBUG_LEVEL>4) && (!quietMode))){
printf("TRB unpack: Found TDC %d Trailer $%04X $%04X\n",TdcId,(dataword>>12)&0xFFF,dataword&0xFFF);
}
if(TdcDataLen!=(dataword&0xFFF)){
if(!quietMode)Error("TRB unpack","TdcDataLen!= length in Trailer!");
if(!quietMode)printf("TRB unpack: TdcDataLen %d != %d ",TdcDataLen,dataword&0xFFF);
}
TdcDataLen=0;
if( nTdcEvtId!=((dataword>>12)&0xFFF)){
if(!quietMode)Error("TRB unpack","TDC Header and Trailer have different EventIds");
}
nCountTDC++;
break;
}
case 4:{
if( ((debugFlag > 0 || DEBUG_LEVEL>4) && (!quietMode))){
printf("TRB unpack: Found TDC %d Lead Data $%08X\n",TdcId,dataword);
}
Int_t nData, nChannel;
nChannel=(dataword>>19)&0x1f;
nChannel+=TdcId*32;
nData=dataword&0x7ffff;
if( ((debugFlag > 0 || DEBUG_LEVEL>4) && (!quietMode))){
printf("(Chan,Data) %3d, %d\n",nChannel,nData);
}
if(trbDataPairFlag){
if(!fill_pair(nChannel,nData&0xFFFF,(nData>>12)&0x7F)){
}
}else{
if(!fill_lead(nChannel,nData)){
}
}
break;
}
case 5:{
if( ((debugFlag > 0 || DEBUG_LEVEL>4) && (!quietMode))){
printf("TRB unpack: Found TDC %d Trail Data $%08X\n",TdcId,dataword);
}
Int_t nData, nChannel;
nChannel=(dataword>>19)&0x1f;
nChannel+=TdcId*32;
nData=dataword&0x7ffff;
if( ((debugFlag > 0 || DEBUG_LEVEL>4) && (!quietMode))){
printf("(Chan,Data) %3d, %d\n",nChannel,nData);
}
if(!fill_trail(nChannel,nData)){
}
break;
}
case 6:{
if((dataword&0x7FFF)==0x1000){
if(!quietMode)Info("TRB unpack","TDC Event Size Limit exceeded!\n");
if(!quietMode)printf("(TDC %d Error Event Size Limit: $%08X)\n",TdcId,dataword);
}else{
if(!quietMode)Info("TRB unpack","Found TDC Error(s)!\n");
if(!quietMode)printf("TDC %d Error $%04X ($%08X)\n",TdcId,dataword&0x7FFF,dataword);
if(!quietMode){
PrintTdcError(dataword&0x7FFF,subEvtId);
}else if(reportCritical && (dataword&0x6000)!=0){
Error("TRB unpack","Found CRITICAL error");
if((dataword&0x2000)!=0){
Error("TRB unpack","Event lost (trigger FIFO overflow)");
printf("TDC %d Error $%04X ($%08X)\n",TdcId,dataword&0x7FFF,dataword);
}else if((dataword&0x4000)!=0){
printf("TDC %d Error $%04X ($%08X)\n",TdcId,dataword&0x7FFF,dataword);
Error("TRB unpack","Internal fatal chip error has been detected");
}
}
}
break;
}
case 7:{
if(!quietMode)Error("TRB unpack","Found DEBUG Info");
if(!quietMode)printf("TRB unpack: TDC %d: Found Debug Info $%08X",TdcId,dataword);
break;
}
default:{
if(!quietMode)Error("TRB unpack","Found UNDEFINED data");
if(!quietMode)printf("TRB unpack: TDC %d: Found undefined $%08X",TdcId,dataword);
break;
}
}
}
if(nCountTDC!=4){
if( nCountTDC<4){
#warning "Comment this in after may06 beamtime"
}else{
if(!quietMode)Error("TRB unpack","TDC count >4 -> additional TDC data!!!");
}
}
if(uBlockSize!=nSizeCounter){
cout<<" --Blok size ="<<uBlockSize<<" , counter Size: "<<nSizeCounter <<endl;
if(!quietMode)Error("TRB unpack","Blocksize!=Counted words!!!");
}
if( ((debugFlag > 0 || DEBUG_LEVEL>4) && (!quietMode))){
printf("==== Unpacker end (%d)\n\n",subEvtId);
}
return(kTRUE);
}
Last change: Sat May 22 13:17:01 2010
Last generated: 2010-05-22 13:17
This page has been automatically generated. If you have any comments or suggestions about the page layout send a mail to ROOT support, or contact the developers with any questions or problems regarding ROOT.