Bug Summary

File:plugins/monitoring/DAQ_online/JEventProcessor_DAQ_online.cc
Location:line 532, column 3
Description:Value stored to 'evio_buffsize' is never read

Annotated Source Code

1// $Id$
2//
3// File: JEventProcessor_DAQ_online.cc
4// Created: Thu Aug 7 09:37:03 EDT 2014
5// Creator: dalton (on Linux gluon05.jlab.org 2.6.32-358.18.1.el6.x86_64 x86_64)
6//
7
8#include <stdint.h>
9#include <vector>
10
11#include "JEventProcessor_DAQ_online.h"
12#include <JANA/JApplication.h>
13#include <JANA/JFactory.h>
14
15using namespace std;
16using namespace jana;
17
18#include <DAQ/DF1TDCHit.h>
19#include <DAQ/Df250PulseIntegral.h>
20#include <DAQ/Df250PulseData.h>
21#include <DAQ/JEventSource_EVIO.h>
22#include <TTAB/DTranslationTable.h>
23
24#include <TDirectory.h>
25#include <TH2.h>
26#include <TH1.h>
27#include <TProfile.h>
28#include <TProfile2D.h>
29#include <TROOT.h>
30
31
32static const int highcratenum=100;
33// root hist pointers
34static TH2I *daq_occ_crates[highcratenum];
35static TProfile2D *daq_ped_crates[highcratenum];
36static TProfile2D *daq_TDClocked_crates[highcratenum];
37static TProfile2D *daq_TDCovr_crates[highcratenum];
38static TProfile *daq_hits_per_event;
39static TProfile *daq_words_per_event;
40static TH1D *daq_event_size;
41static TH1D *daq_event_tdiff;
42static TH1D *daq_words_by_type;
43static bool ttab_labels_set = false;
44
45// Routine used to create our JEventProcessor
46extern "C"{
47 void InitPlugin(JApplication *app){
48 InitJANAPlugin(app);
49 app->AddProcessor(new JEventProcessor_DAQ_online());
50 }
51} // "C"
52
53
54//------------------
55// JEventProcessor_DAQ_online (Constructor)
56//------------------
57JEventProcessor_DAQ_online::JEventProcessor_DAQ_online()
58{
59
60}
61
62//------------------
63// ~JEventProcessor_DAQ_online (Destructor)
64//------------------
65JEventProcessor_DAQ_online::~JEventProcessor_DAQ_online()
66{
67
68}
69
70//------------------
71// init
72//------------------
73jerror_t JEventProcessor_DAQ_online::init(void)
74{
75 printf("JEventProcessor_DAQ_online::init()\n");
76
77 // create root folder for DAQ and cd to it, store main dir
78 maindir = gDirectory(TDirectory::CurrentDirectory());
79 daqdir = maindir->mkdir("DAQ");
80 daqdir->cd();
81
82 // Initialise histograms and variables
83 for (int i=0; i<highcratenum; i++) {
84 daq_occ_crates[i] = NULL__null;
85 daq_ped_crates[i] = NULL__null;
86 daq_TDClocked_crates[i] = NULL__null;
87 daq_TDCovr_crates[i] = NULL__null;
88 }
89
90 daq_hits_per_event = new TProfile("daq_hits_per_event", "Hits/event vs. rocid", 100, 0.5, 100.5);
91 daq_words_per_event = new TProfile("daq_words_per_event", "words/event vs. rocid", 100, 0.5, 100.5);
92 daq_event_size = new TH1D("daq_event_size", "Event size in kB", 1000, 0.0, 1.0E3);
93 daq_event_tdiff = new TH1D("daq_event_tdiff", "Time between events", 10000, 0.0, 1.0E2);
94 daq_words_by_type = new TH1D("daq_words_by_type", "Number of words in EVIO file by type", kNEVIOWordTypes, 0, (double)kNEVIOWordTypes);
95
96 daq_words_per_event->GetXaxis()->SetBinLabel(1 ,"Trigger Bank");
97 daq_words_per_event->GetXaxis()->SetBinLabel(99 ,"Residual");
98
99 daq_event_size->SetXTitle("Total event size (kB)");
100 daq_event_tdiff->SetXTitle("#deltat between events (ms)");
101
102 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kUnknown, "unknown");
103 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kEVIOHeader, "EVIO len. & header");
104 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kEVIOEventNumber, "Event Number Word");
105 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kEVIOTimestamp, "Timestamp");
106
107 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kBORData, "BOR record");
108
109 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf250BlockHeader, "f250 Block Header");
110 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf250BlockTrailer, "f250 Block Trailer");
111 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf250EventHeader, "f250 Event Header");
112 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf250TriggerTime, "f250 Trigger Time");
113 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf250WindowRawData, "f250 Window Raw Data");
114 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf250WindowSum, "f250 Window Sum");
115 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf250PulseRawData, "f250 Pulse Raw Data");
116 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf250PulseIntegral, "f250 Pulse Integral");
117 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf250PulseTime, "f250 Pulse Time");
118 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf250PulsePedestal, "f250 Pulse Pedestal");
119 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf250EventTrailer, "f250 Event Trailer");
120 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf250DataNotValid, "f250 Data Not Valid");
121 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf250Filler, "f250 Filler Word");
122
123 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf125BlockHeader, "f125 Block Header");
124 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf125BlockTrailer, "f125 Block Trailer");
125 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf125EventHeader, "f125 Event Header");
126 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf125TriggerTime, "f125 Trigger Time");
127 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf125WindowRawData, "f125 Window Raw Data");
128 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf125CDCPulse, "f125 CDC Pulse");
129 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf125FDCPulse6, "f125 FDC Pulse (integral)");
130 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf125FDCPulse9, "f125 FDC Pulse (peak)");
131 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf125PulseIntegral, "f125 Pulse Integral");
132 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf125PulseTime, "f125 Pulse Time");
133 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf125PulsePedestal, "f125 Pulse Pedestal");
134 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf125EventTrailer, "f125 Event Trailer");
135 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf125DataNotValid, "f125 Data Not Valid");
136 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kf125Filler, "f125 Filler Word");
137
138 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kF1v2BlockHeader, "F1v2 Block Header");
139 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kF1v2BLockTrailer, "F1v2 Block Trailer");
140 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kF1v2EventHeader, "F1v2 Event Header");
141 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kF1v2TriggerTime, "F1v2 Trigger Time");
142 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kF1v2ChipHeader, "F1v2 Chip Header");
143 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kF1v2Data, "F1v2 Data");
144 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kF1v2Filler, "F1v2 Filler");
145 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kF1v2BreakWord, "F1v2 Break Word");
146
147 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kF1v3BlockHeader, "F1v3 Block Header");
148 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kF1v3BLockTrailer, "F1v3 Block Trailer");
149 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kF1v3EventHeader, "F1v3 Event Header");
150 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kF1v3TriggerTime, "F1v3 Trigger Time");
151 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kF1v3ChipHeader, "F1v3 Chip Header");
152 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kF1v3Data, "F1v3 Data");
153 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kF1v3Filler, "F1v3 Filler");
154 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kF1v3BreakWord, "F1v3 Break Word");
155
156 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kCAEN1190GlobalHeader, "CAEN1190 GLobal Header");
157 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kCAEN1190GlobalTrailer, "CAEN1190 Global Trailer");
158 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kCAEN1190GlobalTriggerTime, "CAEN1190 Trigger Time");
159 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kCAEN1190TDCHeader, "CAEN1190 TDC Header");
160 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kCAEN1190TDCData, "CAEN1190 TDC Data");
161 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kCAEN1190TDCError, "CAEN1190 TDC Error");
162 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kCAEN1190TDCTrailer, "CAEN1190 TDC Trailer");
163 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kCAEN1190Filler, "CAEN1190 Filler");
164
165 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kConfig, "DAQ Config");
166 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kConfigf250, "DAQ Config f250");
167 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kConfigf125, "DAQ Config f125");
168 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kConfigF1, "DAQ Config F1");
169 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kConfigCAEN1190, "DAQ Config CAEN1190");
170
171 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kEPICSheader, "EPICS header");
172 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kEPICSdata, "EPICS data");
173
174 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kF800FAFA, "0xf800fafa");
175 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kD00DD00D, "0xd00dd00d");
176
177 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kTotWords, "Total words in all events");
178 daq_words_by_type->GetXaxis()->SetBinLabel(1 + kNevents, "Number of events");
179
180 // back to main dir
181 maindir->cd();
182
183 return NOERROR;
184}
185
186//------------------
187// AddROCIDLabels
188//------------------
189void JEventProcessor_DAQ_online::AddROCIDLabels(JEventLoop *loop)
190{
191 /// This is called just once to set the x-axis labels
192 /// of histograms whose x-axis is the rocid so that we
193 /// can label them by detector.
194
195 // NO lock: called in init()
196 const DTranslationTable *ttab = NULL__null;
197 loop->GetSingle(ttab);
198
199 // Loop over all rocid values
200 for(uint32_t rocid=2; rocid<99; rocid++){
201 // We don't actually know what slot/channel combos are defined
202 // for this so we loop until we find one.
203 bool found_chan = false;
204 daq_hits_per_event->GetXaxis()->SetBinLabel(rocid, "");
205 daq_words_per_event->GetXaxis()->SetBinLabel(rocid, "");
206 for(uint32_t slot=2; slot<24; slot++){
207 for(uint32_t channel=0; channel<3; channel++){
208 try{
209 DTranslationTable::csc_t csc = {rocid, slot, channel};
210 const DTranslationTable::DChannelInfo &chinfo = ttab->GetDetectorIndex(csc);
211 daq_hits_per_event->GetXaxis()->SetBinLabel(rocid, ttab->DetectorName(chinfo.det_sys).c_str());
212 daq_words_per_event->GetXaxis()->SetBinLabel(rocid, ttab->DetectorName(chinfo.det_sys).c_str());
213 found_chan = true;
214 break;
215 }catch(JException &e){
216 // Do nothing
217 }
218 }
219 if(found_chan) break;
220 }
221 }
222}
223
224//------------------
225// brun
226//------------------
227jerror_t JEventProcessor_DAQ_online::brun(JEventLoop *eventLoop, int32_t runnumber)
228{
229 // This is called whenever the run number changes
230 return NOERROR;
231}
232
233//------------------
234// evnt
235//------------------
236jerror_t JEventProcessor_DAQ_online::evnt(JEventLoop *loop, uint64_t eventnumber)
237{
238 // This is called for every event. Use of common resources like writing
239 // to a file or filling a histogram should be mutex protected. Using
240 // loop->Get(...) to get reconstructed objects (and thereby activating the
241 // reconstruction algorithm) should be done outside of any mutex lock
242 // since multiple threads may call this method at the same time.
243 // Here's an example:
244 vector<const DF1TDCHit*> f1tdchits;
245 vector<const Df250PulseData*> f250PDs;
246 vector<const Df250PulseIntegral*> f250PIs;
247 vector<const Df125PulseIntegral*> f125PIs;
248 vector<const Df125CDCPulse*> f125CDCs;
249 vector<const Df125FDCPulse*> f125FDCs;
250 vector<const DCAEN1290TDCHit*> caen1290hits;
251
252 loop->Get(f1tdchits);
253 loop->Get(f250PDs);
254 loop->Get(f250PIs);
255 loop->Get(f125PIs);
256 loop->Get(f125CDCs);
257 loop->Get(f125FDCs);
258 loop->Get(caen1290hits);
259
260 ParseEventSize(loop->GetJEvent());
261
262 // Set rocid histogram labels based on detector if needed
263 if(!ttab_labels_set){
264 ttab_labels_set = true;
265 AddROCIDLabels(loop);
266 }
267
268 // Initialize counters looking at num. hits per crate
269 uint32_t Nhits_rocid[101];
270 for(uint32_t rocid=0; rocid<101; rocid++) Nhits_rocid[rocid] = 0;
271
272 // Although we are only filling objects local to this plugin, The directory changes: Global ROOT lock
273 japp->RootWriteLock(); //ACQUIRE ROOT LOCK
274
275 if (daqdir!=NULL__null) daqdir->cd();
276
277
278 // Access TDC from DF1TDCHit object
279 for(unsigned int i=0; i<f1tdchits.size(); i++) {
280 const DF1TDCHit *hit = f1tdchits[i];
281 int rocid = hit->rocid;
282 int slot = hit->slot;
283 int channel = hit->channel;
284 int data_word = hit->data_word;
285
286 if(rocid>=0 && rocid<=100) Nhits_rocid[rocid]++;
287
288 if (daq_occ_crates[rocid]==NULL__null) {
289 printf("JEventProcessor_DAQ_online::evnt creating occupancy histogram for crate %i\n",rocid);
290 char cratename[255],title[255];
291 sprintf(cratename,"daq_occ_crate%i",rocid);
292 sprintf(title,"Crate %i occupancy (TDC);Slot;Channel",rocid);
293 daq_occ_crates[rocid] = new TH2I(cratename,title,21,0.5,21.5,32,-0.5,31.5);
294 daq_occ_crates[rocid]->SetStats(0);
295 sprintf(cratename,"daq_TDClocked_crate%i",rocid);
296 sprintf(title,"Crate %i TDC lock status (TDC);Slot;Channel",rocid);
297 daq_TDClocked_crates[rocid] = new TProfile2D(cratename,title,21,0.5,21.5,32,-0.5,31.5);
298 daq_TDClocked_crates[rocid]->SetStats(0);
299 sprintf(cratename,"daq_TDCovr_crate%i",rocid);
300 sprintf(title,"Crate %i TDC overflow status (TDC);Slot;Channel",rocid);
301 daq_TDCovr_crates[rocid] = new TProfile2D(cratename,title,21,0.5,21.5,32,-0.5,31.5);
302 daq_TDCovr_crates[rocid]->SetStats(0);
303
304 }
305 daq_occ_crates[rocid]->Fill(slot,channel);
306 daq_TDClocked_crates[rocid]->Fill(slot,channel,(data_word>>26)&(1));
307 daq_TDCovr_crates[rocid]->Fill(slot,channel,(data_word>>25)&(1));
308 daq_TDCovr_crates[rocid]->Fill(slot,channel,(data_word>>24)&(1));
309 }
310
311 // Access F250 from Df250PulseIntegral object - pre-Fall 2016 firmware
312 for(unsigned int i=0; i<f250PIs.size(); i++) {
313 const Df250PulseIntegral *hit = f250PIs[i];
314 int rocid = hit->rocid;
315 int slot = hit->slot;
316 int channel = hit->channel;
317
318 if(rocid>=0 && rocid<=100) {
319 Nhits_rocid[rocid]++;
320
321 if (daq_occ_crates[rocid]==NULL__null) {
322 printf("JEventProcessor_DAQ_online::evnt creating occupancy histogram for crate %i\n",rocid);
323 char cratename[255],title[255];
324 sprintf(cratename,"daq_occ_crate%i",rocid);
325 sprintf(title,"Crate %i occupancy (F250);Slot;Channel",rocid);
326 daq_occ_crates[rocid] = new TH2I(cratename,title,21,0.5,21.5,16,-0.5,15.5);
327 daq_occ_crates[rocid]->SetStats(0);
328 }
329 daq_occ_crates[rocid]->Fill(slot,channel);
330
331 if (daq_ped_crates[rocid]==NULL__null) {
332 printf("JEventProcessor_DAQ_online::evnt creating pedestal histogram for crate %i\n",rocid);
333 char cratename[255],title[255];
334 sprintf(cratename,"daq_ped_crate%i",rocid);
335 sprintf(title,"Crate %i Average Pedestal (F250);Slot;Channel",rocid);
336 daq_ped_crates[rocid] = new TProfile2D(cratename,title,21,0.5,21.5,16,-0.5,15.5);
337 daq_ped_crates[rocid]->SetStats(0);
338 }
339 if (hit->pedestal > 0) {
340 daq_ped_crates[rocid]->Fill(slot,channel,hit->pedestal);
341 }
342 }
343 }
344
345 // Access F250 from Df250PulseData object - post-Fall 2016 firmware
346 for(unsigned int i=0; i<f250PDs.size(); i++) {
347 const Df250PulseData *hit = f250PDs[i];
348 int rocid = hit->rocid;
349 int slot = hit->slot;
350 int channel = hit->channel;
351
352 if(rocid>=0 && rocid<=100) {
353 Nhits_rocid[rocid]++;
354
355 if (daq_occ_crates[rocid]==NULL__null) {
356 printf("JEventProcessor_DAQ_online::evnt creating occupancy histogram for crate %i\n",rocid);
357 char cratename[255],title[255];
358 sprintf(cratename,"daq_occ_crate%i",rocid);
359 sprintf(title,"Crate %i occupancy (F250);Slot;Channel",rocid);
360 daq_occ_crates[rocid] = new TH2I(cratename,title,21,0.5,21.5,16,-0.5,15.5);
361 daq_occ_crates[rocid]->SetStats(0);
362 }
363 daq_occ_crates[rocid]->Fill(slot,channel);
364
365 if (daq_ped_crates[rocid]==NULL__null) {
366 printf("JEventProcessor_DAQ_online::evnt creating pedestal histogram for crate %i\n",rocid);
367 char cratename[255],title[255];
368 sprintf(cratename,"daq_ped_crate%i",rocid);
369 sprintf(title,"Crate %i Average Pedestal (F250);Slot;Channel",rocid);
370 daq_ped_crates[rocid] = new TProfile2D(cratename,title,21,0.5,21.5,16,-0.5,15.5);
371 daq_ped_crates[rocid]->SetStats(0);
372 }
373 if (hit->pedestal > 0) {
374 daq_ped_crates[rocid]->Fill(slot,channel,hit->pedestal);
375 }
376 }
377 }
378
379 // Access F125 from Df125PulseIntegral object
380 for(unsigned int i=0; i<f125PIs.size(); i++) {
381 const Df125PulseIntegral *hit = f125PIs[i];
382 int rocid = hit->rocid;
383 int slot = hit->slot;
384 int channel = hit->channel;
385
386 if(hit->emulated) continue; // ignore emulated hits
387
388 if(rocid>=0 && rocid<=100) {
389 Nhits_rocid[rocid]++;
390
391 if (daq_occ_crates[rocid]==NULL__null) {
392 printf("JEventProcessor_DAQ_online::evnt creating occupancy histogram for crate %i\n",rocid);
393 char cratename[255],title[255];
394 sprintf(cratename,"daq_occ_crate%i",rocid);
395 sprintf(title,"Crate %i occupancy (F125);Slot;Channel",rocid);
396 daq_occ_crates[rocid] = new TH2I(cratename,title,21,0.5,21.5,16,-0.5,15.5);
397 daq_occ_crates[rocid]->SetStats(0);
398 }
399 daq_occ_crates[rocid]->Fill(slot,channel);
400
401 if (daq_ped_crates[rocid]==NULL__null) {
402 printf("JEventProcessor_DAQ_online::evnt creating pedestal histogram for crate %i\n",rocid);
403 char cratename[255],title[255];
404 sprintf(cratename,"daq_ped_crate%i",rocid);
405 sprintf(title,"Crate %i Average Pedestal (F125);Slot;Channel",rocid);
406 daq_ped_crates[rocid] = new TProfile2D(cratename,title,21,0.5,21.5,16,-0.5,15.5);
407 daq_ped_crates[rocid]->SetStats(0);
408 }
409 if (hit->pedestal > 0) {
410 daq_ped_crates[rocid]->Fill(slot,channel,hit->pedestal);
411 }
412 }
413 }
414
415 // Access F125 from Df125CDCPulse object
416 for(unsigned int i=0; i<f125CDCs.size(); i++) {
417 const Df125CDCPulse *hit = f125CDCs[i];
418 int rocid = hit->rocid;
419 int slot = hit->slot;
420 int channel = hit->channel;
421
422 if(rocid>=0 && rocid<=100) {
423 Nhits_rocid[rocid]++;
424
425 if (daq_occ_crates[rocid]==NULL__null) {
426 printf("JEventProcessor_DAQ_online::evnt creating occupancy histogram for crate %i\n",rocid);
427 char cratename[255],title[255];
428 sprintf(cratename,"daq_occ_crate%i",rocid);
429 sprintf(title,"Crate %i occupancy (F125);Slot;Channel",rocid);
430 daq_occ_crates[rocid] = new TH2I(cratename,title,21,0.5,21.5,16,-0.5,15.5);
431 daq_occ_crates[rocid]->SetStats(0);
432 }
433 daq_occ_crates[rocid]->Fill(slot,channel);
434
435 if (daq_ped_crates[rocid]==NULL__null) {
436 printf("JEventProcessor_DAQ_online::evnt creating pedestal histogram for crate %i\n",rocid);
437 char cratename[255],title[255];
438 sprintf(cratename,"daq_ped_crate%i",rocid);
439 sprintf(title,"Crate %i Average Pedestal (F125);Slot;Channel",rocid);
440 daq_ped_crates[rocid] = new TProfile2D(cratename,title,21,0.5,21.5,16,-0.5,15.5);
441 daq_ped_crates[rocid]->SetStats(0);
442 }
443 if (hit->pedestal > 0) {
444 daq_ped_crates[rocid]->Fill(slot,channel,hit->pedestal);
445 }
446 }
447 }
448
449 // Access F125 from Df125FDCPulse object
450 for(unsigned int i=0; i<f125FDCs.size(); i++) {
451 const Df125FDCPulse *hit = f125FDCs[i];
452 int rocid = hit->rocid;
453 int slot = hit->slot;
454 int channel = hit->channel;
455
456 if(rocid>=0 && rocid<=100) {
457 Nhits_rocid[rocid]++;
458
459 if (daq_occ_crates[rocid]==NULL__null) {
460 printf("JEventProcessor_DAQ_online::evnt creating occupancy histogram for crate %i\n",rocid);
461 char cratename[255],title[255];
462 sprintf(cratename,"daq_occ_crate%i",rocid);
463 sprintf(title,"Crate %i occupancy (F125);Slot;Channel",rocid);
464 daq_occ_crates[rocid] = new TH2I(cratename,title,21,0.5,21.5,16,-0.5,15.5);
465 daq_occ_crates[rocid]->SetStats(0);
466 }
467 daq_occ_crates[rocid]->Fill(slot,channel);
468
469 if (daq_ped_crates[rocid]==NULL__null) {
470 printf("JEventProcessor_DAQ_online::evnt creating pedestal histogram for crate %i\n",rocid);
471 char cratename[255],title[255];
472 sprintf(cratename,"daq_ped_crate%i",rocid);
473 sprintf(title,"Crate %i Average Pedestal (F125);Slot;Channel",rocid);
474 daq_ped_crates[rocid] = new TProfile2D(cratename,title,21,0.5,21.5,16,-0.5,15.5);
475 daq_ped_crates[rocid]->SetStats(0);
476 }
477 if (hit->pedestal > 0) {
478 daq_ped_crates[rocid]->Fill(slot,channel,hit->pedestal);
479 }
480 }
481 }
482
483 // Access CAEN1290 TDC hits
484 for(unsigned int i=0; i<caen1290hits.size(); i++) {
485 const DCAEN1290TDCHit *hit = caen1290hits[i];
486 int rocid = hit->rocid;
487 //int slot = hit->slot;
488 //int channel = hit->channel;
489
490 if(rocid>=0 && rocid<=100) Nhits_rocid[rocid]++;
491 }
492
493 // Fill in hits by crate
494 for(uint32_t rocid=0; rocid<101; rocid++) daq_hits_per_event->Fill(rocid, Nhits_rocid[rocid]);
495
496 maindir->cd();
497 // Unlock ROOT
498 japp->RootUnLock(); //RELEASE ROOT LOCK
499
500 return NOERROR;
501}
502
503//------------------
504// ParseEventSize
505//------------------
506void JEventProcessor_DAQ_online::ParseEventSize(JEvent &event)
507{
508 /// This ugliness is needed to get at the true banks for each event by rocid.
509
510 // Bombproof
511 if(event.GetJEventSource()->className() != string("JEventSource_EVIO")){
512 static bool warned = false;
513 if(!warned){
514 cout << "WARNING: This is not an event source of type JEventSource_EVIO!" << endl;
515 cout << " Event size statistics filling unavailable!" << endl;
516 warned = true;
517 }
518 return;
519 }
520
521 void *ref = event.GetRef();
522 if(!ref) return;
523 uint32_t *istart = JEventSource_EVIO::GetEVIOBufferFromRef(ref);
524 uint32_t evio_buffsize = JEventSource_EVIO::GetEVIOBufferSizeFromRef(ref);
525 uint32_t evio_buffwords = evio_buffsize/sizeof(uint32_t);
526 uint32_t *iend = &istart[evio_buffwords];
527
528 if( istart==NULL__null ) return;
529 if( (evio_buffwords>=10) && (istart[7]==0xc0da0100) ){
530 // NTH is first 8 words so skip them
531 istart= &istart[8];
532 evio_buffsize -= 8*sizeof(uint32_t);
Value stored to 'evio_buffsize' is never read
533 evio_buffwords -= 8;
534 }
535
536 // Check if this is BOR data
537 if( evio_buffwords >= 4 ){
538 uint32_t mask = (0x70<<16) | (0x01);
539 if( (istart[1]&mask) == mask ){
540
541 // FILL HISTOGRAMS
542 // Since we are filling histograms local to this plugin, it will not interfere with other ROOT operations: can use plugin-wide ROOT fill lock
543 japp->RootFillLock(this); //ACQUIRE ROOT FILL LOCK
544 daq_words_by_type->Fill(kBORData, istart[0]/sizeof(uint32_t));
545 japp->RootFillUnLock(this); //RELEASE ROOT FILL LOCK
546 return; // no further parsing needed
547 }
548 }
549
550 // Check if this is EPICS data
551 if( evio_buffwords >= 4 ){
552 if( istart[1] == (0x60<<16) + (0xD<<8) + (0x1<<0) ){
553 if( istart[2] == (0x61<<24) + (0x1<<16) + (0x1<<0) ){
554
555 // FILL HISTOGRAMS
556 // Since we are filling histograms local to this plugin, it will not interfere with other ROOT operations: can use plugin-wide ROOT fill lock
557 japp->RootFillLock(this); //ACQUIRE ROOT FILL LOCK
558 daq_words_by_type->Fill(kEPICSheader, 3.0); // EVIO outer and segment headers + timestamp
559 daq_words_by_type->Fill(kEPICSdata, istart[0]/sizeof(uint32_t) - 3);
560 japp->RootFillUnLock(this); //RELEASE ROOT FILL LOCK
561 return; // no further parsing needed
562 }
563 }
564 }
565
566 if( evio_buffwords < 4 ){
567 cout << "Too few words in event (" << evio_buffwords << ") skipping..." << endl;
568 return;
569 }
570
571 // Physics event length
572 uint32_t physics_event_len = istart[0];
573 if( (istart[1] & 0xFF001000) != 0xFF001000 ) return; // not a physics event
574 if( physics_event_len+1 > evio_buffwords ){
575 cout << "Too many words in physics event: " << physics_event_len+1 << " > " << evio_buffwords << endl;
576 return;
577 }
578
579 // Trigger bank event length
580 uint32_t trigger_bank_len = istart[2];
581 if( (istart[3] & 0xFF202000) != 0xFF202000 ) return; // not a trigger bank
582 uint64_t tlo = istart[2+5];
583 uint64_t thi = istart[2+6];
584 uint64_t timestamp = (thi<<32) + (tlo<<0);
585 if( trigger_bank_len+2 > evio_buffwords ){
586 cout << "Too many words in trigger bank " << trigger_bank_len << " > " << evio_buffwords-2 << endl;
587 return;
588 }
589
590 // Allocate memory to hold stats data
591 uint32_t Nwords[100]; // total data words for each ROC (includes event length words)
592 uint32_t word_stats[kNEVIOWordTypes]; // obtained from parsing event
593 for(uint32_t rocid=0; rocid<100; rocid++) Nwords[rocid] = 0;
594 for(uint32_t i=0; i<kNEVIOWordTypes; i++) word_stats[i] = 0;
595
596 word_stats[kNevents]++;
597 word_stats[kTotWords] += evio_buffwords;
598
599 word_stats[kEVIOHeader] += 4; // physics event and built trigger bank length and header words
600
601 // Loop over data banks
602 uint32_t *iptr = &istart[3+trigger_bank_len];
603 while(iptr < iend){
604
605 uint32_t len = *iptr;
606 uint32_t rocid = (iptr[1]>>16) & 0XFF;
607
608 if(rocid<100) Nwords[rocid] += len+1;
609
610 word_stats[kEVIOHeader] += 2; // ROC data bank length and header words
611
612 uint32_t *imyend = &iptr[len+1];
613 if(imyend > iend) imyend = iend;
614
615 uint64_t Nwords = ((uint64_t)imyend - (uint64_t)iptr)/sizeof(uint32_t);
616 if(Nwords<2){
617 static int Nwarnings = 0;
618 if(Nwarnings<10){
619 cout << "Nwords<2 (?)" << endl;
620 cout << " evio_buffwords = " << evio_buffwords << endl;
621 cout << " physics_event_len = " << physics_event_len << endl;
622 cout << " trigger_bank_len = " << trigger_bank_len << endl;
623 event.Print();
624 if(++Nwarnings == 10) cout << "Last warning!" << endl;
625 }
626 break;
627 }
628
629 DataWordStats(iptr, imyend, word_stats);
630
631 iptr = &iptr[len +1];
632 }
633
634 // FILL HISTOGRAMS
635 // Since we are filling histograms local to this plugin, it will not interfere with other ROOT operations: can use plugin-wide ROOT fill lock
636 japp->RootFillLock(this); //ACQUIRE ROOT FILL LOCK
637
638 // Calculating time between events is tricky when using multiple-threads.
639 // We need the timestamp of two sequential events, but the order in which
640 // they are processed here will likely not be in event order. Thus, we keep
641 // a running list of the last 128 timestamps and event numbers seen by this
642 // routine. We can then search this for the event prior to this one and if
643 // found, use it.
644 uint32_t event_num = event.GetEventNumber();
645 static uint32_t recent_event_nums[128];
646 static uint64_t recent_timestamps[128];
647 static uint32_t ievent = 0;
648 for(uint32_t i=0; i<ievent; i++){
649 if(i>=128) break;
650 if(recent_event_nums[i] == (event_num-1)){
651 double tdiff = (double)(timestamp - recent_timestamps[i])/250.0E6; // convert to seconds
652 daq_event_tdiff->Fill(tdiff*1000.0); // ms
653 break;
654 }
655 }
656
657 // Record this timestamp/event number in the ring buffer
658 uint32_t idx = ievent%128;
659 recent_event_nums[idx] = event_num;
660 recent_timestamps[idx] = timestamp;
661 ievent++;
662
663 // Fill event size histos
664 double physics_event_len_kB = (double)((physics_event_len+1)*sizeof(uint32_t))/1024.0;
665 daq_event_size->Fill(physics_event_len_kB);
666 uint32_t TotalWords = 0;
667 for(uint32_t rocid=0; rocid<100; rocid++){
668 daq_words_per_event->Fill(rocid, Nwords[rocid]);
669 TotalWords += Nwords[rocid];
670 }
671
672 daq_words_per_event->Fill(1, trigger_bank_len+1);
673 daq_words_per_event->Fill(99, physics_event_len - trigger_bank_len - TotalWords);
674
675 for(uint32_t i=0; i<kNEVIOWordTypes; i++){
676 daq_words_by_type->Fill(i, (double)word_stats[i]);
677 }
678
679 japp->RootFillUnLock(this); //RELEASE ROOT FILL LOCK
680}
681
682//------------------
683// DataWordStats
684//------------------
685void JEventProcessor_DAQ_online::DataWordStats(uint32_t *iptr, uint32_t *iend, uint32_t *word_stats)
686{
687 // Upon entry, the iptr will point to the start of the "Physics Event's Data Bank".
688 // It will loop over all sub-banks, tallying the word count as it goes up to
689 // but not including iend.
690
691 iptr++; // advance past length word
692 uint32_t rocid = (*iptr++)>>16 & 0x0FFF;
693 while(iptr < iend){
694 uint32_t data_block_bank_len = *iptr++;
695 uint32_t *iendbank = &iptr[data_block_bank_len];
696 uint32_t det_id = ((*iptr) >> 16) & 0x0FFF;
697
698 if(iendbank > iend) iendbank = iend;
699
700 word_stats[kEVIOHeader] += 2; // data block bank length and header words
701
702 iptr++; // advance to first raw data word
703
704 uint32_t Ntoprocess = data_block_bank_len - 1; // 1 for bank header
705
706#if 0 // I don't know if these words are actually implmented ??
707 word_stats[kEVIOEventNumber]++; // starting event number
708 word_stats[kEVIOTimestamp] += 2; // 48-bit timestamp
709 iptr++; // starting event number
710 iptr++; // 48-bit timestamp
711 iptr++; // 48-bit timestamp
712 Ntoprocess -= 3;
713#endif
714 uint32_t *irawdata = iptr;
715
716 switch(det_id){
717 case 0:
718 case 1:
719 case 3:
720 case 6: // flash 250 module, MMD 2014/2/4
721 case 16: // flash 125 module (CDC), DL 2014/6/19
722 case 26: // F1 TDC module (BCAL), MMD 2014-07-31
723 ParseJLabModuleData(rocid, iptr, iendbank, word_stats);
724 break;
725
726 case 20:
727 ParseCAEN1190(rocid, iptr, iendbank, word_stats);
728 break;
729
730 case 0x55:
731 ParseModuleConfiguration(rocid, iptr, iendbank, word_stats);
732 break;
733
734 default:
735 break;
736 }
737
738 uint32_t Nprocessed = (uint32_t)((uint64_t)iptr - (uint64_t)irawdata)/sizeof(uint32_t);
739 if(Nprocessed < Ntoprocess) word_stats[kUnknown] += Ntoprocess - Nprocessed;
740 iptr = iendbank;
741 }
742
743
744}
745
746//------------------
747// ParseJLabModuleData
748//------------------
749void JEventProcessor_DAQ_online::ParseJLabModuleData(uint32_t rocid, uint32_t *&iptr, uint32_t *iend, uint32_t *word_stats)
750{
751 while(iptr < iend){
752 if(*iptr != 0xf800fafa) break;
753 word_stats[kF800FAFA]++;
754 iptr++;
755 }
756
757 uint32_t mod_id = ((*iptr) >> 18) & 0x000F;
758 switch(mod_id){
759 case DModuleType::FADC250: Parsef250Bank(rocid, iptr, iend, word_stats); break;
760 case DModuleType::FADC125: Parsef125Bank(rocid, iptr, iend, word_stats); break;
761 case DModuleType::F1TDC32: ParseF1v2TDCBank(rocid, iptr, iend, word_stats); break;
762 case DModuleType::F1TDC48: ParseF1v3TDCBank(rocid, iptr, iend, word_stats); break;
763 //case DModuleType::JLAB_TS: ParseTSBank(rocid, iptr, iend, word_stats); break;
764 //case DModuleType::TID: ParseTIBank(rocid, iptr, iend, word_stats); break;
765 }
766}
767
768//------------------
769// Parsef250Bank
770//------------------
771void JEventProcessor_DAQ_online::Parsef250Bank(uint32_t rocid, uint32_t *&iptr, uint32_t *iend, uint32_t *word_stats)
772{
773 while(iptr<iend){
774
775 if(((*iptr>>31) & 0x1) == 0) { word_stats[kUnknown]++ ; iptr++; continue;}
776
777 uint32_t window_width;
778 uint32_t window_words;
779 uint32_t data_type = (*iptr>>27) & 0x0F;
780 switch(data_type){
781 case 0: word_stats[kf250BlockHeader]++; iptr++; break;
782 case 1: word_stats[kf250BlockTrailer]++; iptr++; break;
783 case 2: word_stats[kf250EventHeader]++; iptr++; break;
784 case 3: // Trigger time
785 word_stats[kf250TriggerTime]++;
786 iptr++;
787 if(((*iptr>>31) & 0x1) == 0){ word_stats[kf250TriggerTime]++; iptr++; }
788 break;
789 case 4: // Window Raw Data
790 window_width = (*iptr>>0) & 0x0FFF;
791 window_words = 1 + ((window_width+1)/2); // 1 is for header word + 2 sample per word
792 word_stats[kf250WindowRawData] += window_words;
793 iptr = &iptr[window_words];
794 break;
795 case 7: word_stats[kf250PulseIntegral]++; iptr++; break;
796 case 8: word_stats[kf250PulseTime]++; iptr++; break;
797 case 10: word_stats[kf250PulsePedestal]++; iptr++; break;
798 case 13: word_stats[kf250EventTrailer]++; iptr++; break;
799 case 14: word_stats[kf250DataNotValid]++; iptr++; break;
800 case 15: word_stats[kf250Filler]++; iptr++; break;
801
802 default: word_stats[kUnknown]++; iptr++; break;
803 }
804 }
805}
806
807//------------------
808// Parsef125Bank
809//------------------
810void JEventProcessor_DAQ_online::Parsef125Bank(uint32_t rocid, uint32_t *&iptr, uint32_t *iend, uint32_t *word_stats)
811{
812 while(iptr<iend){
813
814 if(((*iptr>>31) & 0x1) == 0) { word_stats[kUnknown]++ ; iptr++; continue;}
815
816 uint32_t window_width;
817 uint32_t window_words;
818 uint32_t data_type = (*iptr>>27) & 0x0F;
819 switch(data_type){
820 case 0: word_stats[kf125BlockHeader]++; iptr++; break;
821 case 1: word_stats[kf125BlockTrailer]++; iptr++; break;
822 case 2: word_stats[kf125EventHeader]++; iptr++; break;
823 case 3: // Trigger time
824 word_stats[kf125TriggerTime]++;
825 iptr++;
826 if(((*iptr>>31) & 0x1) == 0){ word_stats[kf125TriggerTime]++; iptr++; }
827 break;
828 case 4: // Window Raw Data
829 window_width = (*iptr>>0) & 0x0FFF;
830 window_words = 1 + ((window_width+1)/2); // 1 is for header word + 2 sample per word
831 word_stats[kf125WindowRawData] += window_words;
832 iptr = &iptr[window_words];
833 break;
834 case 5: word_stats[kf125CDCPulse]++;
835 iptr++;
836 if(((*iptr>>31) & 0x1) == 0){ word_stats[kf125CDCPulse]++; iptr++; }
837 break;
838 case 6: word_stats[kf125FDCPulse6]++;
839 iptr++;
840 if(((*iptr>>31) & 0x1) == 0){ word_stats[kf125FDCPulse6]++; iptr++; }
841 break;
842 case 7: word_stats[kf125PulseIntegral]++; iptr++; break;
843 case 8: word_stats[kf125PulseTime]++; iptr++; break;
844 case 9: word_stats[kf125FDCPulse9]++;
845 iptr++;
846 if(((*iptr>>31) & 0x1) == 0){ word_stats[kf125FDCPulse9]++; iptr++; }
847 break;
848 case 10: word_stats[kf125PulsePedestal]++; iptr++; break;
849 case 13: word_stats[kf125EventTrailer]++; iptr++; break;
850 case 14: word_stats[kf125DataNotValid]++; iptr++; break;
851 case 15: word_stats[kf125Filler]++; iptr++; break;
852
853 default: word_stats[kUnknown]++; iptr++; break;
854 }
855 }
856}
857
858//------------------
859// ParseF1v2TDCBank
860//------------------
861void JEventProcessor_DAQ_online::ParseF1v2TDCBank(uint32_t rocid, uint32_t *&iptr, uint32_t *iend, uint32_t *word_stats)
862{
863 while(iptr<iend){
864 switch( (*iptr++) & 0xF8000000 ){
865 case 0xC0000000: word_stats[kF1v2ChipHeader]++; break;
866 case 0xB8000000: word_stats[kF1v2Data]++; break;
867 case 0xF8000000: word_stats[kF1v2Filler]++; break;
868 case 0x80000000: word_stats[kF1v2BlockHeader]++; break;
869 case 0x88000000: word_stats[kF1v2BLockTrailer]++; break;
870 case 0x90000000: word_stats[kF1v2EventHeader]++; break;
871 case 0x98000000: word_stats[kF1v2TriggerTime]++; break;
872 case 0xF0000000: word_stats[kF1v2BreakWord]++; break;
873 default: word_stats[kUnknown]++; break;
874 }
875 }
876}
877
878//------------------
879// ParseF1v3TDCBank
880//------------------
881void JEventProcessor_DAQ_online::ParseF1v3TDCBank(uint32_t rocid, uint32_t *&iptr, uint32_t *iend, uint32_t *word_stats)
882{
883 while(iptr<iend){
884 switch( (*iptr++) & 0xF8000000 ){
885 case 0xC0000000: word_stats[kF1v3ChipHeader]++; break;
886 case 0xB8000000: word_stats[kF1v3Data]++; break;
887 case 0xF8000000: word_stats[kF1v3Filler]++; break;
888 case 0x80000000: word_stats[kF1v3BlockHeader]++; break;
889 case 0x88000000: word_stats[kF1v3BLockTrailer]++; break;
890 case 0x90000000: word_stats[kF1v3EventHeader]++; break;
891 case 0x98000000: word_stats[kF1v3TriggerTime]++; break;
892 case 0xF0000000: word_stats[kF1v3BreakWord]++; break;
893 default: word_stats[kUnknown]++; break;
894 }
895 }
896}
897
898//------------------
899// ParseCAEN1190
900//------------------
901void JEventProcessor_DAQ_online::ParseCAEN1190(uint32_t rocid, uint32_t *&iptr, uint32_t *iend, uint32_t *word_stats)
902{
903 while(iptr<iend){
904
905 // This word appears to be appended to the data.
906 // Probably in the ROL. Ignore it if found.
907 if(*iptr == 0xd00dd00d) {
908 word_stats[kD00DD00D]++;
909 iptr++;
910 continue;
911 }
912
913 uint32_t type = (*iptr++) >> 27;
914 switch(type){
915 case 0b01000: word_stats[kCAEN1190GlobalHeader]++; break;
916 case 0b10000: word_stats[kCAEN1190GlobalTrailer]++; break;
917 case 0b10001: word_stats[kCAEN1190GlobalTriggerTime]++; break;
918 case 0b00001: word_stats[kCAEN1190TDCHeader]++; break;
919 case 0b00000: word_stats[kCAEN1190TDCData]++; break;
920 case 0b00100: word_stats[kCAEN1190TDCError]++; break;
921 case 0b00011: word_stats[kCAEN1190TDCTrailer]++; break;
922 case 0b11000: word_stats[kCAEN1190Filler]++; break;
923 default: word_stats[kUnknown]++; break;
924 }
925 }
926}
927
928//------------------
929// ParseModuleConfiguration
930//------------------
931void JEventProcessor_DAQ_online::ParseModuleConfiguration(uint32_t rocid, uint32_t *&iptr, uint32_t *iend, uint32_t *word_stats)
932{
933 while(iptr < iend){
934
935 word_stats[kConfig]++; // Count headers as generic
936 uint32_t Nvals = ((*iptr++) >> 24) & 0xFF;
937
938 // Loop over all parameters in this section
939 for(uint32_t i=0; i< Nvals; i++){
940
941 switch((*iptr++)>>24){
942 case 0x05: word_stats[kConfigf250]++; break;
943 case 0x0F: word_stats[kConfigf125]++; break;
944 case 0x06: word_stats[kConfigF1]++; break;
945 case 0x10: word_stats[kConfigCAEN1190]++; break;
946 default: word_stats[kConfig]++; break;
947 }
948 }
949 }
950}
951
952//------------------
953// erun
954//------------------
955jerror_t JEventProcessor_DAQ_online::erun(void)
956{
957 // This is called whenever the run number changes, before it is
958 // changed to give you a chance to clean up before processing
959 // events from the next run number.
960
961 // FILL HISTOGRAMS
962 // Since we are filling histograms local to this plugin, it will not interfere with other ROOT operations: can use plugin-wide ROOT fill lock
963 japp->RootFillLock(this); //ACQUIRE ROOT FILL LOCK
964
965 for (int i=0; i<highcratenum; i++) {
966 if (daq_occ_crates[i] != NULL__null) {
967 daq_occ_crates[i]->SetMinimum(daq_occ_crates[i]->GetMinimum(0.001));
968 }
969 if (daq_ped_crates[i] != NULL__null) {
970 daq_ped_crates[i]->SetMinimum(daq_ped_crates[i]->GetMinimum(0.001));
971 }
972 if (daq_TDClocked_crates[i] != NULL__null) {
973 daq_TDClocked_crates[i]->SetMinimum(daq_TDClocked_crates[i]->GetMinimum(0.001));
974 }
975 if (daq_TDCovr_crates[i] != NULL__null) {
976 daq_TDCovr_crates[i]->SetMinimum(daq_TDCovr_crates[i]->GetMinimum(0.001));
977 }
978 }
979
980 japp->RootFillUnLock(this); //RELEASE ROOT FILL LOCK
981
982 return NOERROR;
983}
984
985//------------------
986// fini
987//------------------
988jerror_t JEventProcessor_DAQ_online::fini(void)
989{
990 // Called before program exit after event processing is finished.
991 return NOERROR;
992}
993