8 #include "Stl3Util/gl3/gl3Conductor.h"
10 #include "Stl3Util/base/L3swap.h"
11 #include "Stl3Util/base/realcc.h"
12 #include "Stl3Util/base/FtfLog.h"
16 #include <netinet/in.h>
20 #include <sys/types.h>
21 #include <sys/socket.h>
31 gl3Conductor::gl3Conductor (
void){
32 unsigned int start = realcc();
34 unsigned int stop = realcc();
37 ccPerMs = (double)(stop-start)/1000.;
47 gl3Conductor::~gl3Conductor ( ) {
49 if ( event != NULL )
delete[] event ;
51 if ( algorithm != NULL )
delete algorithm;
52 if ( summary != NULL )
delete[] summary ;
53 if ( summaryData != NULL ) free (summaryData) ;
60 int gl3Conductor::configure (
L3_CFG *cfg)
64 if(cfg == NULL || cfg == (
L3_CFG *)-1) {
65 ftfLog(
"gl3Conductor::configure: No configuration information found.\n");
71 for (
int i=0; i<GL3_ALG_MAX_NUM; i++) {
72 if(ntohl(algos[i].alg_id) != 0) {
74 gl3InstantiateAlgorithm(ntohl(algos[i].alg_id));
77 ftfLog(
"gl3Conductor::configure: Instantiation of algorithm #%d failed.\n", i);
82 algo->setScaling(ntohl(algos[i].preScale),
83 ntohl(algos[i].postScale));
85 if (algo->setParameters(ntohl(algos[i].GI1),
94 fswap(algos[i].GF5))) {
95 ftfLog(
"gl3Conductor::configure: Invalid parameters for algorithm %s (ID %d)", algo->getAlgorithmName(), algo->getAlgorithmID());
101 ftfLog(
"gl3Conductor::configure: Appending algorithm %s (ID %i) to list failed.\n",
102 algo->getAlgorithmName(), algo->getAlgorithmID());
106 algo->showConfiguration();
119 if ( nAlgorithms >= maxAlgorithms ) {
120 ftfLog (
"gl3Conductor::add: Max. number of algorithms reached\n" ) ;
123 algorithm[nAlgorithms] = module ;
132 void gl3Conductor::clearAlgorithms()
134 for (
int i =0; i<nAlgorithms; i++) {
148 int gl3Conductor::checkHistoRequest ( ) {
150 struct sockaddr_in remoteAddress;
151 socklen_t sin_size =
sizeof(
struct sockaddr_in);
153 if ((remoteSocket = accept(socketFd, (
struct sockaddr *)&remoteAddress,
158 const int maxBytes = 100000 ;
159 char* buffer =
new char[maxBytes];
161 int nBytes = writeHistos ( maxBytes, buffer ) ;
164 ftfLog (
"gl3Conductor::checkHistoRequest: buffer too small \n " ) ;
167 int nSend = send(remoteSocket, buffer, nBytes, 0 ) ;
168 ftfLog (
"gl3Conductor: %d out of %d bytes sent\n ", nSend, nBytes ) ;
181 int gl3Conductor::end ( ){
185 for (
int i = 0 ; i < nAlgorithms ; i++ ) {
186 algorithm[i]->end( );
195 gl3Event* gl3Conductor::getEvent (
int token ) {
197 int index = getTokenIndex(token) ;
202 return &(
event[index]) ;
209 int gl3Conductor::init ( ){
211 ftfLog(
"gl3Conductor::init: %d algos\n", nAlgorithms);
216 nAlgorithms+2, -2.5, (
double)nAlgorithms-0.5);
218 histoList.push_back(l3Rates);
220 allocateTimingHistos();
223 for (
int i = 0 ; i < nAlgorithms ; i++ ) {
224 algorithm[i]->init();
244 if ( desc && desc->token != l3data->bh.token ) {
245 ftfLog (
"gl3Conductor::readEvent: token mismatch (%d and %d)\n",
246 desc->token, l3data->bh.token);
250 int token = l3data->bh.token;
254 if ( token < 0 || token > maxTokens ){
255 ftfLog (
"gl3Conductor::readEvent: %d token out of bounds\n", token );
260 int index = getFreeEventIndex();
262 ftfLog (
"gl3Conductor::readEvent: No free event container \n" ) ;
265 tokenIndex[token] = index;
269 if (event[index].readEventDescriptor(desc) != 0) {
270 ftfLog (
"gl3Conductor::processEvent: error reading EventDescriptor\n" ) ;
275 if ( event[index].getTrgCmd() == 0 ||
276 event[index].getTrgCmd() == 1 ||
277 event[index].getTrgCmd() == 2 ||
278 event[index].getTrgCmd() == 3 ) {
279 ftfLog (
"gl3Conductor::processEvent: Trigger Command 0,1,2 or 3 received\n");
283 if ( event[index].getTrgCmd() == 5 ||
284 event[index].getTrgCmd() == 6 ||
285 event[index].getTrgCmd() == 7 ) {
286 ftfLog (
"gl3Conductor::processEvent: Trigger Command 5,6 or 7 received - unknown physics run type\n");
291 if ( event[index].readL3Data(l3data) != 0 ) {
292 ftfLog (
"gl3Conductor::processEvent: error reading L3 data\n" ) ;
299 if ( event[index].getTrgCmd() >= 8 ) {
306 if ( event[index].readTrgData(trgSum, trgRaw) != 0 ) {
307 ftfLog (
"gl3Conductor::processEvent: error reading TRG data\n" ) ;
317 for (
int i = 0 ; i < nAlgorithms ; i++ ) {
318 int alg_decision = algorithm[i]->process( &(event[index]));
319 if (alg_decision > decision) {
320 decision = alg_decision;
329 for (
int i = 0 ; i < nAlgorithms ; i++ ) {
330 algorithm[i]->incrementCounters();
333 collectSummary(token);
344 for (
int i=0; i<nAlgorithms;i++) {
346 if (summaryData[index].alg[i].accept)
358 if ( communicationsFlag ) {
363 if (nAlgorithms == 0) decision=1;
374 int gl3Conductor::fillSummary(
int token,
376 struct L3_SUMD *summaryDataDest)
378 int index = getTokenIndex(token);
379 if (index < 0)
return 1;
381 memcpy(summaryDest, &summary[index],
sizeof(
L3_summary));
383 memcpy(summaryDataDest, &summaryData[index],
384 summaryData[index].bh.length*4);
392 int gl3Conductor::collectSummary(
int token)
394 int index = tokenIndex[token];
395 if (index < 0)
return 1;
397 sprintf(summaryData->bh.bank_type, CHAR_L3_SUMD);
398 summaryData[index].bh.length =
400 summaryData[index].bh.bank_id = 0;
401 summaryData[index].bh.format_ver = 0;
402 summaryData[index].bh.byte_order = DAQ_RAW_FORMAT_ORDER;
403 summaryData[index].bh.format_number = 0;
404 summaryData[index].bh.token = token;
405 summaryData[index].bh.w9 = DAQ_RAW_FORMAT_WORD9;
406 summaryData[index].bh.crc = 0;
408 summaryData[index].nProcessed = 0;
409 summaryData[index].nReconstructed = nReco;
410 summaryData[index].nAlg = nAlgorithms;
412 summary[index].accept = 0;
413 summary[index].build = 0;
414 summary[index].on = 0;
416 for (
int i = 0; i < nAlgorithms; i++) {
417 algorithm[i]->fillSummary(&summaryData[index].alg[i]);
419 if(summaryData[index].alg[i].on)
420 summary[index].on |= 1<<i;
422 if(summaryData[index].alg[i].accept)
423 summary[index].accept |= 1<<i;
425 if(summaryData[index].alg[i].build)
426 summary[index].build |= 1<<i;
430 summary[index].nTracks =
event[index].getNTracks();
438 int gl3Conductor::releaseToken (
int token ) {
439 int index = getTokenIndex(token);
440 if (index < 0)
return 1;
442 event[index].resetEvent();
448 int gl3Conductor::resetHistos ( ) {
449 list<gl3Histo*>::iterator histo;
450 for(histo=histoList.begin(); histo!=histoList.end(); histo++) {
459 int gl3Conductor::runStart (
int _runNumber ) {
460 runNumber = _runNumber ;
461 for (
int i = 0 ; i < nAlgorithms ; i++ ) {
462 algorithm[i]->init();
466 return resetHistos ( ) ;
471 int gl3Conductor::runEnd ( ) {
472 for (
int i = 0 ; i < nAlgorithms ; i++ ) {
473 algorithm[i]->end( );
480 int gl3Conductor::setCommunications ( ){
483 struct sockaddr_in gl3Address;
488 if ((socketFd = socket(AF_INET, SOCK_STREAM, 0)) == -1) {
489 ftfLog(
"setCommunications socket: %s",strerror(errno) );
492 fcntl(socketFd, F_SETFL, O_NONBLOCK);
495 gl3Address.sin_family = AF_INET;
496 gl3Address.sin_port = htons(gl3Port);
497 gl3Address.sin_addr.s_addr = INADDR_ANY;
498 bzero(&(gl3Address.sin_zero), 8);
500 if (bind(socketFd, (
struct sockaddr *)&gl3Address,
501 sizeof(
struct sockaddr)) == -1) {
502 ftfLog(
"setCommunications bind: %s",strerror(errno) );
506 if (listen(socketFd, backLog) == -1) {
507 ftfLog(
"setCommunications listen: %s",strerror(errno) );
517 void gl3Conductor::setBField (
float bField ){
518 for (
int i = 0 ; i < maxEvents ; i++ ) {
519 event[i].setBField ( bField ) ;
525 void gl3Conductor::setHitProcessing (
int hitPro ){
526 hitProcessing = hitPro ;
527 for (
int i = 0 ; i < maxEvents ; i++ ) {
528 event[i].setHitProcessing ( hitPro ) ;
534 void gl3Conductor::setMaxSectorNForTrackMerging (
int _maxSectorNForTrackMerging ){
535 maxSectorNForTrackMerging = _maxSectorNForTrackMerging ;
536 for (
int i = 0 ; i < maxEvents ; i++ ) {
537 event[i].setMaxSectorNForTrackMerging ( _maxSectorNForTrackMerging ) ;
544 int maxEventsIn,
int maxAlgorithmsIn ) {
546 communicationsFlag = 1 ;
551 tokenIndex =
new int[maxTokens+1];
554 maxEvents = maxEventsIn ;
555 maxAlgorithms = maxAlgorithmsIn ;
564 for (
int i=0; i<maxAlgorithms;i++) algorithm[i]=NULL;
569 for (
int i = 0 ; i < maxTokens ; i++ ) tokenIndex[i] = 0 ;
575 if ( communicationsFlag ){
576 if(setCommunications() )
582 for (
int i = 0 ; i < maxEvents ; i++ ) {
583 event[i].setHitProcessing ( hitProcessing ) ;
584 event[i].setCoordinateTransformer ( _trans ) ;
587 ftfLog(
"analysis framework set up\n");
594 int gl3Conductor::writeHistos (
int maxBytes,
char *buffer )
599 ftfLog (
"nHistos %d \n", histoList.size() ) ;
600 container->runNumber = runNumber ;
601 container->nHistos = histoList.size();
603 char* pointer = (
char *)&(container->buffer) ;
604 char* endBuffer = buffer + maxBytes ;
609 list<gl3Histo*>::iterator histo;
610 for(histo=histoList.begin(); histo!=histoList.end(); histo++) {
612 nBytes = (*histo)->Write ( endBuffer-pointer, pointer ) ;
614 ftfLog (
"gl3Container::writeHistos %d byte long buffer is too short \n", maxBytes ) ;
618 nTotalBytes += nBytes ;
619 if ( nTotalBytes > maxBytes ) {
620 ftfLog (
"gl3Conductor::writeHistos: nTotalBytes %d max %d\n", nTotalBytes, maxBytes ) ;
623 pointer += nBytes *
sizeof(char) ;
625 container->nBytes = nTotalBytes ;
626 ftfLog (
"gl3Conductor::writeHistos: histos %d Bytes %d \n",
627 histoList.size(), nTotalBytes ) ;
637 int gl3Conductor::getFreeEventIndex()
639 int freeEventIndex = -1 ;
640 for (
int i = 0 ; i < maxEvents ; i++ ) {
641 if ( !(event[i].getBusy() ) ) {
648 return freeEventIndex;
654 int gl3Conductor::getTokenIndex(
int token)
656 if (token < 0 || token > 4096) {
657 ftfLog(
"gl3Conductor: token [%d] out of bounds \n", token );
661 int index = tokenIndex[token];
663 if (index < 0 || index >= maxTokens) {
664 ftfLog(
"gl3Conductor: event index %d out of bounds \n", token );
676 void gl3Conductor::resetTimer()
682 cpuTimes.reserve(5+nAlgorithms);
683 realTimes.reserve(5+nAlgorithms);
688 void gl3Conductor::timingMark()
690 cpuTimes[lastTimeEntry] = clock();
691 realTimes[lastTimeEntry] = realcc();
696 void gl3Conductor::allocateTimingHistos()
699 timingHistos.resize(3+nAlgorithms);
701 timingHistos[0] =
new gl3Histo(
"time_read_l3",
702 "Timing: read L3 data",
705 timingHistos[1] =
new gl3Histo(
"time_read_trg",
706 "Timing: read TRG data",
709 char hid[30], htitle[100];
710 for(
int i=0; i<nAlgorithms;i++) {
712 sprintf(hid,
"time_alg_%d", i);
713 sprintf(htitle,
"Timing: algorithms %d", i);
714 timingHistos[2+i] =
new gl3Histo(hid, htitle,
718 timingHistos[2+nAlgorithms] =
new gl3Histo(
"time_total",
724 for(
int i=0;i<timingHistos.size();i++) {
725 histoList.push_back(timingHistos[i]);
730 void gl3Conductor::fillTimingHistos()
733 timingHistos[0]->Fill(
double(realTimes[1] - realTimes[0])/ccPerMs);
734 timingHistos[1]->Fill(
double(realTimes[2] - realTimes[1])/ccPerMs);
736 for(
int i=0; i<nAlgorithms;i++) {
737 timingHistos[2+i]->Fill(
double(realTimes[3+i] - realTimes[2+i])/ccPerMs);
740 timingHistos[2+nAlgorithms]->
741 Fill(
double(realTimes[lastTimeEntry-1] - realTimes[0])/ccPerMs);
743 ftfLog(
"total time: %f\n",
744 double(realTimes[lastTimeEntry-1] - realTimes[0])/ccPerMs);
748 void gl3Conductor::printTiming()
750 for (
int i=1; i<lastTimeEntry;i++) {
751 ftfLog(
"gl3Conductor: timing step %2d: CPU: %8f real: %8f\n",
752 i, (
double)cpuTimes[i]-cpuTimes[i-1]/CLOCKS_PER_SEC,
753 (
double)(realTimes[i]-realTimes[i-1])/ccPerMs);
int Fill(double x, double weight=1)
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! ...