00001 #include "get4/Processor.h"
00002
00003 #include <stdlib.h>
00004 #include <stdio.h>
00005 #include <math.h>
00006
00007 #include <algorithm>
00008
00009 #include "base/commons.h"
00010 #include "base/ProcMgr.h"
00011
00012 #include "get4/SubEvent.h"
00013
00014 get4::Get4Rec::Get4Rec() :
00015 used(false),
00016 fChannels(0)
00017 {
00018 for(unsigned n=0;n<NumChannels;n++) {
00019 fRisTm[n] = 0;
00020 fFalTm[n] = 0;
00021 lastRisingEdge[0] = 0;
00022 }
00023 }
00024
00025
00026
00027 get4::Processor::Processor(unsigned rocid, unsigned get4mask) :
00028 base::SysCoreProc("ROC", rocid),
00029 fIter(),
00030 fIter2()
00031 {
00032 mgr()->RegisterProc(this, roc::proc_RocEvent, rocid);
00033
00034
00035
00036 fMsgsKind = MakeH1("MsgKind", "kind of messages", 8, 0, 8, "xbin:NOP,-,EPOCH,SYNC,AUX,EPOCH2,GET4,SYS;kind");
00037 fSysTypes = MakeH1("SysTypes", "Distribution of system messages", 16, 0, 16, "systype");
00038
00039 CreateBasicHistograms();
00040
00041
00042
00043 for (unsigned get4=0; (get4<16) && (get4mask!=0); get4++) {
00044 GET4.push_back(Get4Rec());
00045 GET4[get4].used = (get4mask & 1) == 1;
00046 get4mask = get4mask >> 1;
00047 if (!GET4[get4].used) continue;
00048
00049 SetSubPrefix("GET4_", get4);
00050
00051 GET4[get4].fChannels = MakeH1("Channels", "GET4 channels", 8, 0, 4., "ch");
00052
00053 for(unsigned n=0;n<NumChannels;n++) {
00054 SetSubPrefix("GET4_", get4, "Ch", n);
00055
00056 GET4[get4].fRisTm[n] = MakeH1("RisingTm", "rising edge time", 1024*8, 0, 1024.*512, "bin");
00057
00058 GET4[get4].fRisFineTm[n] = MakeH1("RisingFine", "rising fine time", 128, 0, 128, "bin");
00059
00060 GET4[get4].fFalTm[n] = MakeH1("FallingTm", "falling edge time", 1024*8, 0, 1024.*512, "bin");
00061
00062 GET4[get4].fFalFineTm[n] = MakeH1("FallingFine", "falling fine time", 128, 0, 128, "bin");
00063
00064 GET4[get4].fWidth[n] = MakeH1("Width", "time-over-threshold", 1024, 0, 1024, "bin");
00065
00066 GET4[get4].fRisRef[n] = 0;
00067 GET4[get4].fFalRef[n] = 0;
00068 }
00069 }
00070
00071 SetSubPrefix("");
00072
00073
00074
00075 SetNoSyncSource();
00076 SetNoTriggerSignal();
00077
00078 fRefGet4 = 9999;
00079 fRefChannel = NumChannels;
00080
00081 fNumHits = 0;
00082 fNumBadHits = 0;
00083 }
00084
00085 get4::Processor::~Processor()
00086 {
00087
00088
00089
00090 printf("get4::Processor::~Processor\n");
00091 }
00092
00093 void get4::Processor::setRefChannel(unsigned ref_get4, unsigned ref_ch)
00094 {
00095 fRefGet4 = ref_get4;
00096 fRefChannel = ref_ch;
00097 if (!isRefChannel()) return;
00098
00099 for (unsigned get4=0; get4<GET4.size(); get4++) {
00100 if (!GET4[get4].used) continue;
00101
00102 for(unsigned ch=0;ch<NumChannels;ch++) {
00103 SetSubPrefix("GET4_", get4, "Ch", ch);
00104
00105 GET4[get4].fRisRef[ch] = MakeH1("Rising_to_Ref", "difference to ref signal, rising edge", 1024*8, -4096., 4096., "bin");
00106 GET4[get4].fFalRef[ch] = MakeH1("Falling_to_Ref", "difference to ref signal, falling edge", 1024*8, -4096., 4096., "bin");
00107 }
00108 }
00109
00110 }
00111
00112
00113 void get4::Processor::AssignBufferTo(roc::Iterator& iter, const base::Buffer& buf)
00114 {
00115 if (buf.null()) return;
00116
00117 iter.setFormat(buf().format);
00118 iter.setRocNumber(buf().boardid);
00119
00120 unsigned msglen = roc::Message::RawSize(buf().format);
00121
00122
00123 iter.assign(buf().buf, buf().datalen - msglen);
00124 }
00125
00126
00127
00128 bool get4::Processor::FirstBufferScan(const base::Buffer& buf)
00129 {
00130 if (buf.null()) return false;
00131
00132 AssignBufferTo(fIter, buf);
00133
00134 roc::Message& msg = fIter.msg();
00135
00136 unsigned cnt(0), msgcnt(0);
00137
00138 bool first = true;
00139
00140
00141
00142
00143
00144
00145
00146 while (fIter.next()) {
00147
00148 cnt++;
00149
00150
00151 if (fIter.islast() && msg.isEpochMsg()) continue;
00152
00153 unsigned rocid = msg.getRocNumber();
00154
00155 if (rocid != GetBoardId()) {
00156 printf("Message from wrong ROCID %u, expected %u\n", rocid, GetBoardId());
00157 continue;
00158 }
00159
00160 msgcnt++;
00161
00162 FillH1(fMsgsKind, msg.getMessageType());
00163
00164
00165
00166
00167
00168 if (first && !msg.isEpochMsg()) {
00169 first = false;
00170 buf().local_tm = fIter.getMsgFullTimeD();
00171 }
00172
00173
00174 double msgtm = (fIter.getMsgFullTime() % 1000000000000LLU)*1e-9;
00175
00176 FillH1(fALLt, msgtm);
00177
00178
00179 switch (msg.getMessageType()) {
00180
00181 case roc::MSG_NOP:
00182 break;
00183
00184 case roc::MSG_HIT: {
00185 printf("FAILURE - no any nXYTER hits in GET4 processor!!!\n");
00186 exit(5);
00187 break;
00188 }
00189
00190 case roc::MSG_EPOCH: {
00191 break;
00192 }
00193
00194 case roc::MSG_GET4: {
00195
00196
00197 unsigned get4 = msg.getGet4Number();
00198 if (!get4_in_use(get4)) break;
00199
00200 unsigned ch = msg.getGet4ChNum();
00201 unsigned edge = msg.getGet4Edge();
00202 unsigned ts = msg.getGet4Ts();
00203 uint64_t fulltm = fIter.getMsgFullTime();
00204
00205
00206 FillH1(GET4[get4].fChannels, ch + edge*0.5);
00207
00208 if ((get4==fRefGet4) && (ch == fRefChannel) && (edge==0)) {
00209 base::LocalTriggerMarker marker;
00210 marker.localid = 1000 + get4*16 + ch*2 + edge;
00211 marker.localtm = fIter.getMsgFullTimeD();
00212
00213
00214
00215 AddTriggerMarker(marker);
00216
00217 }
00218
00219
00220 if ((get4==fRefGet4) && (ch == fRefChannel)) {
00221
00222 if (edge==0)
00223 fLastRefRising = fulltm;
00224 else
00225 fLastRefFalling = fulltm;
00226
00227
00228 for (unsigned ii=0; ii<GET4.size(); ii++) {
00229 if (!GET4[ii].used) continue;
00230
00231 for(unsigned jj=0;jj<NumChannels;jj++) {
00232 if (edge==0)
00233 FillH1(GET4[ii].fRisRef[jj], Get4TimeDiff(fLastRefRising, GET4[ii].lastRisingEdge[jj]));
00234 else
00235 FillH1(GET4[ii].fFalRef[jj], Get4TimeDiff(fLastRefFalling, GET4[ii].lastFallingEdge[jj]));
00236 }
00237 }
00238
00239 }
00240
00241 if (edge==0) {
00242 FillH1(GET4[get4].fRisTm[ch], ts);
00243 FillH1(GET4[get4].fRisFineTm[ch], ts % 128);
00244 GET4[get4].lastRisingEdge[ch] = fulltm;
00245
00246 if (isRefChannel())
00247 FillH1(GET4[get4].fRisRef[ch], Get4TimeDiff(fLastRefRising, fulltm));
00248
00249 } else {
00250 FillH1(GET4[get4].fFalTm[ch], ts);
00251 FillH1(GET4[get4].fFalFineTm[ch], ts % 128);
00252 GET4[get4].lastFallingEdge[ch] = fulltm;
00253
00254 FillH1(GET4[get4].fWidth[ch], GET4[get4].lastFallingEdge[ch] - GET4[get4].lastRisingEdge[ch]);
00255
00256 if (isRefChannel())
00257 FillH1(GET4[get4].fFalRef[ch], Get4TimeDiff(fLastRefFalling, fulltm));
00258 }
00259
00260
00261 break;
00262 }
00263
00264 case roc::MSG_EPOCH2: {
00265 break;
00266 }
00267
00268 case roc::MSG_SYNC: {
00269 unsigned sync_ch = msg.getSyncChNum();
00270
00271
00272 FillH1(fSYNCt[sync_ch], msgtm);
00273
00274
00275 if (sync_ch == fSyncSource) {
00276
00277 base::SyncMarker marker;
00278 marker.uniqueid = msg.getSyncData();
00279 marker.localid = msg.getSyncChNum();
00280 marker.local_stamp = fIter.getMsgFullTime();
00281 marker.localtm = fIter.getMsgFullTimeD();
00282
00283
00284
00285
00286
00287
00288
00289 AddSyncMarker(marker);
00290 }
00291
00292 if (fTriggerSignal == (10 + sync_ch)) {
00293
00294 base::LocalTriggerMarker marker;
00295 marker.localid = 10 + sync_ch;
00296 marker.localtm = fIter.getMsgFullTimeD();
00297
00298 AddTriggerMarker(marker);
00299 }
00300
00301 break;
00302 }
00303
00304 case roc::MSG_AUX: {
00305 unsigned auxid = msg.getAuxChNum();
00306
00307 FillH1(fAUXt[auxid], msgtm);
00308
00309 if (fTriggerSignal == auxid) {
00310
00311 base::LocalTriggerMarker marker;
00312 marker.localid = auxid;
00313 marker.localtm = fIter.getMsgFullTimeD();
00314
00315 AddTriggerMarker(marker);
00316 }
00317
00318 break;
00319 }
00320
00321 case roc::MSG_SYS: {
00322 FillH1(fSysTypes, msg.getSysMesType());
00323 break;
00324 }
00325 }
00326
00327 }
00328
00329 FillMsgPerBrdHist(msgcnt);
00330
00331 return true;
00332 }
00333
00334 unsigned get4::Processor::GetTriggerMultipl(unsigned indx)
00335 {
00336 get4::SubEvent* ev = (get4::SubEvent*) fGlobalTrig[indx].subev;
00337
00338 return ev ? ev->fExtMessages.size() : 0;
00339 }
00340
00341
00342 bool get4::Processor::SecondBufferScan(const base::Buffer& buf)
00343 {
00344 if (buf.null()) return false;
00345
00346
00347
00348
00349
00350 AssignBufferTo(fIter2, buf);
00351
00352 roc::Message& msg = fIter2.msg();
00353
00354 unsigned cnt(0);
00355
00356 unsigned help_index = 0;
00357
00358 while (fIter2.next()) {
00359
00360 cnt++;
00361
00362
00363 if (fIter2.islast() && msg.isEpochMsg()) continue;
00364
00365 unsigned rocid = msg.getRocNumber();
00366
00367 if (rocid != GetBoardId()) continue;
00368
00369
00370
00371 switch (msg.getMessageType()) {
00372
00373 case roc::MSG_NOP:
00374 break;
00375
00376 case roc::MSG_SYNC:
00377 case roc::MSG_AUX:
00378 case roc::MSG_HIT:
00379 break;
00380
00381
00382 case roc::MSG_GET4: {
00383 base::GlobalTime_t localtm = fIter2.getMsgFullTimeD();
00384
00385 base::GlobalTime_t globaltm = LocalToGlobalTime(localtm, &help_index);
00386
00387 unsigned indx = TestHitTime(globaltm, get4_in_use(msg.getGet4Number()));
00388
00389 if ((indx < fGlobalTrig.size()) && !fGlobalTrig[indx].isflush) {
00390 get4::SubEvent* ev = (get4::SubEvent*) fGlobalTrig[indx].subev;
00391
00392 if (ev==0) {
00393 ev = new get4::SubEvent;
00394 fGlobalTrig[indx].subev = ev;
00395 }
00396
00397 ev->fExtMessages.push_back(get4::MessageExtended(msg, globaltm));
00398 }
00399 break;
00400 }
00401
00402 case roc::MSG_EPOCH:
00403 break;
00404
00405 case roc::MSG_EPOCH2:
00406 break;
00407
00408 case roc::MSG_SYS:
00409 break;
00410 }
00411
00412 }
00413
00414 return true;
00415 }
00416
00417 void get4::Processor::SortDataInSubEvent(base::SubEvent* subev)
00418 {
00419 get4::SubEvent* nxsub = (get4::SubEvent*) subev;
00420
00421 std::sort(nxsub->fExtMessages.begin(), nxsub->fExtMessages.end());
00422 }
00423