/[PAMELA software]/PamelaDigitizer/Digitizer.cxx
ViewVC logotype

Diff of /PamelaDigitizer/Digitizer.cxx

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 1.3 by orsi, Thu Oct 11 11:29:21 2007 UTC revision 1.5 by silvio, Wed Nov 28 18:54:31 2007 UTC
# Line 1  Line 1 
1  //               ------ PAMELA Digitizer ------  //               ------ PAMELA Digitizer ------
2  //  //
3  // Date, release and how-to: see file Pamelagp2Digits.cxx  // Date, release and how-to: see file Pamelagp2Digits.cxx
4  //  //
5  // NB: Check length physics packet [packet type (0x10 = physics data)]  // NB: Check length physics packet [packet type (0x10 = physics data)]
6  //  //
7  #include <sstream>  #include <sstream>
8  #include <fstream>  #include <fstream>
9  #include <stdlib.h>  #include <stdlib.h>
10  #include <stdio.h>  #include <stdio.h>
11  #include <string.h>  #include <string.h>
12  #include <ctype.h>  #include <ctype.h>
13  #include <time.h>  #include <time.h>
14  #include "Riostream.h"  #include "Riostream.h"
15  #include "TFile.h"  #include "TFile.h"
16  #include "TDirectory.h"  #include "TDirectory.h"
17  #include "TTree.h"  #include "TTree.h"
18  #include "TLeafI.h"  #include "TLeafI.h"
19  #include "TH1.h"  #include "TH1.h"
20  #include "TH2.h"  #include "TH2.h"
21  #include "TMath.h"  #include "TMath.h"
22  #include "TRandom.h"  #include "TRandom.h"
23  #include "TSQLServer.h"  #include "TSQLServer.h"
24  #include "TSystem.h"  #include "TSystem.h"
25  //  //
26  #include "Digitizer.h"  #include "Digitizer.h"
27  #include "CRC.h"  #include "CRC.h"
28  //  //
29  #include <PamelaRun.h>  #include <PamelaRun.h>
30  #include <physics/calorimeter/CalorimeterEvent.h>  #include <physics/calorimeter/CalorimeterEvent.h>
31  #include <CalibCalPedEvent.h>  #include <CalibCalPedEvent.h>
32  #include "GLTables.h"  #include "GLTables.h"
33  //  //
34  extern "C"{  extern "C"{
35    short crc(short, short);    short crc(short, short);
36  };  };
37  //  //
38    
39  Digitizer::Digitizer(TTree* tree, char* &file_raw){  Digitizer::Digitizer(TTree* tree, char* &file_raw){
40    fhBookTree = tree;    fhBookTree = tree;
41    fFilename =  file_raw;    fFilename =  file_raw;
42    fCounter = 0;    fCounter = 0;
43    fOBT = 0;    fOBT = 0;
44    
45    //    //
46    // DB connections    // DB connections
47    //    //
48    TString host = "mysql://localhost/pamelaprod";    TString host = "mysql://localhost/pamelaprod";
49    TString user = "anonymous";    TString user = "anonymous";
50    TString psw = "";    TString psw = "";
51    //    //
52    const char *pamdbhost=gSystem->Getenv("PAM_DBHOST");    const char *pamdbhost=gSystem->Getenv("PAM_DBHOST");
53    const char *pamdbuser=gSystem->Getenv("PAM_DBUSER");    const char *pamdbuser=gSystem->Getenv("PAM_DBUSER");
54    const char *pamdbpsw=gSystem->Getenv("PAM_DBPSW");    const char *pamdbpsw=gSystem->Getenv("PAM_DBPSW");
55    if ( !pamdbhost ) pamdbhost = "";    if ( !pamdbhost ) pamdbhost = "";
56    if ( !pamdbuser ) pamdbuser = "";    if ( !pamdbuser ) pamdbuser = "";
57    if ( !pamdbpsw ) pamdbpsw = "";    if ( !pamdbpsw ) pamdbpsw = "";
58    if ( strcmp(pamdbhost,"") ) host = pamdbhost;    if ( strcmp(pamdbhost,"") ) host = pamdbhost;
59    if ( strcmp(pamdbuser,"") ) user = pamdbuser;    if ( strcmp(pamdbuser,"") ) user = pamdbuser;
60    if ( strcmp(pamdbpsw,"") ) psw = pamdbpsw;    if ( strcmp(pamdbpsw,"") ) psw = pamdbpsw;
61    fDbc = TSQLServer::Connect(host.Data(),user.Data(),psw.Data());    fDbc = TSQLServer::Connect(host.Data(),user.Data(),psw.Data());
62    //    //
63    GL_TABLES *glt = new GL_TABLES(host,user,psw);    GL_TABLES *glt = new GL_TABLES(host,user,psw);
64    if ( glt->IsConnected(fDbc) ) printf("\n DB INFORMATION:\n SQL: %s Version: %s Host %s Port %i \n\n",fDbc->GetDBMS(),fDbc->ServerInfo(),fDbc->GetHost(),fDbc->GetPort());    if ( glt->IsConnected(fDbc) ) printf("\n DB INFORMATION:\n SQL: %s Version: %s Host %s Port %i \n\n",fDbc->GetDBMS(),fDbc->ServerInfo(),fDbc->GetHost(),fDbc->GetPort());
65    //    //
66    // Use UTC in the DB and make timeout bigger    // Use UTC in the DB and make timeout bigger
67    //    //
68    stringstream myquery;    stringstream myquery;
69    myquery.str("");    myquery.str("");
70    myquery << "SET time_zone='+0:00'";    myquery << "SET time_zone='+0:00'";
71    fDbc->Query(myquery.str().c_str());    fDbc->Query(myquery.str().c_str());
72    myquery.str("");    myquery.str("");
73    myquery << "SET wait_timeout=173000;";    myquery << "SET wait_timeout=173000;";
74    fDbc->Query(myquery.str().c_str());    fDbc->Query(myquery.str().c_str());
75    //    //
76        
77    std:: cout << "preparing tree" << endl;    std:: cout << "preparing tree" << endl;
78    
79    // prepare tree    // prepare tree
80    fhBookTree->SetBranchAddress("Irun",&Irun);    fhBookTree->SetBranchAddress("Irun",&Irun);
81    fhBookTree->SetBranchAddress("Ievnt",&Ievnt);    fhBookTree->SetBranchAddress("Ievnt",&Ievnt);
82    fhBookTree->SetBranchAddress("Ipa",&Ipa);    fhBookTree->SetBranchAddress("Ipa",&Ipa);
83    fhBookTree->SetBranchAddress("X0",&X0);    fhBookTree->SetBranchAddress("X0",&X0);
84    fhBookTree->SetBranchAddress("Y0",&Y0);    fhBookTree->SetBranchAddress("Y0",&Y0);
85    fhBookTree->SetBranchAddress("Z0",&Z0);    fhBookTree->SetBranchAddress("Z0",&Z0);
86    fhBookTree->SetBranchAddress("Theta",&Theta);    fhBookTree->SetBranchAddress("Theta",&Theta);
87    fhBookTree->SetBranchAddress("Phi",&Phi);    fhBookTree->SetBranchAddress("Phi",&Phi);
88    fhBookTree->SetBranchAddress("P0",&P0);    fhBookTree->SetBranchAddress("P0",&P0);
89    fhBookTree->SetBranchAddress("Nthtof",&Nthtof);    fhBookTree->SetBranchAddress("Nthtof",&Nthtof);
90    fhBookTree->SetBranchAddress("Ipltof",Ipltof);    fhBookTree->SetBranchAddress("Ipltof",Ipltof);
91    fhBookTree->SetBranchAddress("Ipaddle",Ipaddle);    fhBookTree->SetBranchAddress("Ipaddle",Ipaddle);
92    fhBookTree->SetBranchAddress("Ipartof",Ipartof);    fhBookTree->SetBranchAddress("Ipartof",Ipartof);
93    fhBookTree->SetBranchAddress("Xintof",Xintof);    fhBookTree->SetBranchAddress("Xintof",Xintof);
94    fhBookTree->SetBranchAddress("Yintof",Yintof);    fhBookTree->SetBranchAddress("Yintof",Yintof);
95    fhBookTree->SetBranchAddress("Zintof",Zintof);    fhBookTree->SetBranchAddress("Zintof",Zintof);
96    fhBookTree->SetBranchAddress("Xouttof",Xouttof);    fhBookTree->SetBranchAddress("Xouttof",Xouttof);
97    fhBookTree->SetBranchAddress("Youttof",Youttof);    fhBookTree->SetBranchAddress("Youttof",Youttof);
98    fhBookTree->SetBranchAddress("Zouttof",Zouttof);    fhBookTree->SetBranchAddress("Zouttof",Zouttof);
99    fhBookTree->SetBranchAddress("Ereltof",Ereltof);    fhBookTree->SetBranchAddress("Ereltof",Ereltof);
100    fhBookTree->SetBranchAddress("Timetof",Timetof);    fhBookTree->SetBranchAddress("Timetof",Timetof);
101    fhBookTree->SetBranchAddress("Pathtof",Pathtof);    fhBookTree->SetBranchAddress("Pathtof",Pathtof);
102    fhBookTree->SetBranchAddress("P0tof",P0tof);    fhBookTree->SetBranchAddress("P0tof",P0tof);
103    fhBookTree->SetBranchAddress("Nthcat",&Nthcat);    fhBookTree->SetBranchAddress("Nthcat",&Nthcat);
104    fhBookTree->SetBranchAddress("Iparcat",Iparcat);    fhBookTree->SetBranchAddress("Iparcat",Iparcat);
105    fhBookTree->SetBranchAddress("Icat",Icat);    fhBookTree->SetBranchAddress("Icat",Icat);
106    fhBookTree->SetBranchAddress("Xincat",Xincat);    fhBookTree->SetBranchAddress("Xincat",Xincat);
107    fhBookTree->SetBranchAddress("Yincat",Yincat);    fhBookTree->SetBranchAddress("Yincat",Yincat);
108    fhBookTree->SetBranchAddress("Zincat",Zincat);    fhBookTree->SetBranchAddress("Zincat",Zincat);
109    fhBookTree->SetBranchAddress("Xoutcat",Xoutcat);    fhBookTree->SetBranchAddress("Xoutcat",Xoutcat);
110    fhBookTree->SetBranchAddress("Youtcat",Youtcat);    fhBookTree->SetBranchAddress("Youtcat",Youtcat);
111    fhBookTree->SetBranchAddress("Zoutcat",Zoutcat);    fhBookTree->SetBranchAddress("Zoutcat",Zoutcat);
112    fhBookTree->SetBranchAddress("Erelcat",Erelcat);    fhBookTree->SetBranchAddress("Erelcat",Erelcat);
113    fhBookTree->SetBranchAddress("Timecat",Timecat);    fhBookTree->SetBranchAddress("Timecat",Timecat);
114    fhBookTree->SetBranchAddress("Pathcat",Pathcat);    fhBookTree->SetBranchAddress("Pathcat",Pathcat);
115    fhBookTree->SetBranchAddress("P0cat",P0cat);    fhBookTree->SetBranchAddress("P0cat",P0cat);
116    fhBookTree->SetBranchAddress("Nthcas",&Nthcas);    fhBookTree->SetBranchAddress("Nthcas",&Nthcas);
117    fhBookTree->SetBranchAddress("Iparcas",Iparcas);    fhBookTree->SetBranchAddress("Iparcas",Iparcas);
118    fhBookTree->SetBranchAddress("Icas",Icas);    fhBookTree->SetBranchAddress("Icas",Icas);
119    fhBookTree->SetBranchAddress("Xincas",Xincas);    fhBookTree->SetBranchAddress("Xincas",Xincas);
120    fhBookTree->SetBranchAddress("Yincas",Yincas);    fhBookTree->SetBranchAddress("Yincas",Yincas);
121    fhBookTree->SetBranchAddress("Zincas",Zincas);    fhBookTree->SetBranchAddress("Zincas",Zincas);
122    fhBookTree->SetBranchAddress("Xoutcas",Xoutcas);    fhBookTree->SetBranchAddress("Xoutcas",Xoutcas);
123    fhBookTree->SetBranchAddress("Youtcas",Youtcas);    fhBookTree->SetBranchAddress("Youtcas",Youtcas);
124    fhBookTree->SetBranchAddress("Zoutcas",Zoutcas);    fhBookTree->SetBranchAddress("Zoutcas",Zoutcas);
125    fhBookTree->SetBranchAddress("Erelcas",Erelcas);    fhBookTree->SetBranchAddress("Erelcas",Erelcas);
126    fhBookTree->SetBranchAddress("Timecas",Timecas);    fhBookTree->SetBranchAddress("Timecas",Timecas);
127    fhBookTree->SetBranchAddress("Pathcas",Pathcas);    fhBookTree->SetBranchAddress("Pathcas",Pathcas);
128    fhBookTree->SetBranchAddress("P0cas",P0cas);    fhBookTree->SetBranchAddress("P0cas",P0cas);
129    fhBookTree->SetBranchAddress("Nthspe",&Nthspe);    fhBookTree->SetBranchAddress("Nthspe",&Nthspe);
130    fhBookTree->SetBranchAddress("Iparspe",Iparspe);    fhBookTree->SetBranchAddress("Iparspe",Iparspe);
131    fhBookTree->SetBranchAddress("Itrpb",Itrpb);    fhBookTree->SetBranchAddress("Itrpb",Itrpb);
132    fhBookTree->SetBranchAddress("Itrsl",Itrsl);    fhBookTree->SetBranchAddress("Itrsl",Itrsl);
133    fhBookTree->SetBranchAddress("Itspa",Itspa);    fhBookTree->SetBranchAddress("Itspa",Itspa);
134    fhBookTree->SetBranchAddress("Xinspe",Xinspe);    fhBookTree->SetBranchAddress("Xinspe",Xinspe);
135    fhBookTree->SetBranchAddress("Yinspe",Yinspe);    fhBookTree->SetBranchAddress("Yinspe",Yinspe);
136    fhBookTree->SetBranchAddress("Zinspe",Zinspe);    fhBookTree->SetBranchAddress("Zinspe",Zinspe);
137    fhBookTree->SetBranchAddress("Xoutspe",Xoutspe);    fhBookTree->SetBranchAddress("Xoutspe",Xoutspe);
138    fhBookTree->SetBranchAddress("Youtspe",Youtspe);    fhBookTree->SetBranchAddress("Youtspe",Youtspe);
139    fhBookTree->SetBranchAddress("Zoutspe",Zoutspe);    fhBookTree->SetBranchAddress("Zoutspe",Zoutspe);
140    fhBookTree->SetBranchAddress("Xavspe",Xavspe);    fhBookTree->SetBranchAddress("Xavspe",Xavspe);
141    fhBookTree->SetBranchAddress("Yavspe",Yavspe);    fhBookTree->SetBranchAddress("Yavspe",Yavspe);
142    fhBookTree->SetBranchAddress("Zavspe",Zavspe);    fhBookTree->SetBranchAddress("Zavspe",Zavspe);
143    fhBookTree->SetBranchAddress("Erelspe",Erelspe);    fhBookTree->SetBranchAddress("Erelspe",Erelspe);
144    fhBookTree->SetBranchAddress("Pathspe",Pathspe);    fhBookTree->SetBranchAddress("Pathspe",Pathspe);
145    fhBookTree->SetBranchAddress("P0spe",P0spe);    fhBookTree->SetBranchAddress("P0spe",P0spe);
146    fhBookTree->SetBranchAddress("Nxmult",Nxmult);    fhBookTree->SetBranchAddress("Nxmult",Nxmult);
147    fhBookTree->SetBranchAddress("Nymult",Nymult);    fhBookTree->SetBranchAddress("Nymult",Nymult);
148    fhBookTree->SetBranchAddress("Nstrpx",&Nstrpx);    fhBookTree->SetBranchAddress("Nstrpx",&Nstrpx);
149    fhBookTree->SetBranchAddress("Npstripx",Npstripx);    fhBookTree->SetBranchAddress("Npstripx",Npstripx);
150    fhBookTree->SetBranchAddress("Ntstripx",Ntstripx);    fhBookTree->SetBranchAddress("Ntstripx",Ntstripx);
151    fhBookTree->SetBranchAddress("Istripx",Istripx);    fhBookTree->SetBranchAddress("Istripx",Istripx);
152    fhBookTree->SetBranchAddress("Qstripx",Qstripx);    fhBookTree->SetBranchAddress("Qstripx",Qstripx);
153    fhBookTree->SetBranchAddress("Xstripx",Xstripx);    fhBookTree->SetBranchAddress("Xstripx",Xstripx);
154    fhBookTree->SetBranchAddress("Nstrpy",&Nstrpy);    fhBookTree->SetBranchAddress("Nstrpy",&Nstrpy);
155    fhBookTree->SetBranchAddress("Npstripy",Npstripy);    fhBookTree->SetBranchAddress("Npstripy",Npstripy);
156    fhBookTree->SetBranchAddress("Ntstripy",Ntstripy);    fhBookTree->SetBranchAddress("Ntstripy",Ntstripy);
157    fhBookTree->SetBranchAddress("Istripy",Istripy);    fhBookTree->SetBranchAddress("Istripy",Istripy);
158    fhBookTree->SetBranchAddress("Qstripy",Qstripy);    fhBookTree->SetBranchAddress("Qstripy",Qstripy);
159    fhBookTree->SetBranchAddress("Ystripy",Ystripy);    fhBookTree->SetBranchAddress("Ystripy",Ystripy);
160    fhBookTree->SetBranchAddress("Nthcali",&Nthcali);    fhBookTree->SetBranchAddress("Nthcali",&Nthcali);
161    fhBookTree->SetBranchAddress("Icaplane",Icaplane);    fhBookTree->SetBranchAddress("Icaplane",Icaplane);
162    fhBookTree->SetBranchAddress("Icastrip",Icastrip);    fhBookTree->SetBranchAddress("Icastrip",Icastrip);
163    fhBookTree->SetBranchAddress("Icamod",Icamod);    fhBookTree->SetBranchAddress("Icamod",Icamod);
164    fhBookTree->SetBranchAddress("Enestrip",Enestrip);    fhBookTree->SetBranchAddress("Enestrip",Enestrip);
165    fhBookTree->SetBranchAddress("Nthcal",&Nthcal);    fhBookTree->SetBranchAddress("Nthcal",&Nthcal);
166    fhBookTree->SetBranchAddress("Icapl",Icapl);    fhBookTree->SetBranchAddress("Icapl",Icapl);
167    fhBookTree->SetBranchAddress("Icasi",Icasi);    fhBookTree->SetBranchAddress("Icasi",Icasi);
168    fhBookTree->SetBranchAddress("Icast",Icast);    fhBookTree->SetBranchAddress("Icast",Icast);
169    fhBookTree->SetBranchAddress("Xincal",Xincal);    fhBookTree->SetBranchAddress("Xincal",Xincal);
170    fhBookTree->SetBranchAddress("Yincal",Yincal);    fhBookTree->SetBranchAddress("Yincal",Yincal);
171    fhBookTree->SetBranchAddress("Zincal",Zincal);    fhBookTree->SetBranchAddress("Zincal",Zincal);
172    fhBookTree->SetBranchAddress("Erelcal",Erelcal);    fhBookTree->SetBranchAddress("Erelcal",Erelcal);
173    fhBookTree->SetBranchAddress("Nthnd",&Nthnd);    fhBookTree->SetBranchAddress("Nthnd",&Nthnd);
174    fhBookTree->SetBranchAddress("Itubend",Itubend);    fhBookTree->SetBranchAddress("Itubend",Itubend);
175    fhBookTree->SetBranchAddress("Iparnd",Iparnd);    fhBookTree->SetBranchAddress("Iparnd",Iparnd);
176    fhBookTree->SetBranchAddress("Xinnd",Xinnd);    fhBookTree->SetBranchAddress("Xinnd",Xinnd);
177    fhBookTree->SetBranchAddress("Yinnd",Yinnd);    fhBookTree->SetBranchAddress("Yinnd",Yinnd);
178    fhBookTree->SetBranchAddress("Zinnd",Zinnd);    fhBookTree->SetBranchAddress("Zinnd",Zinnd);
179    fhBookTree->SetBranchAddress("Xoutnd",Xoutnd);    fhBookTree->SetBranchAddress("Xoutnd",Xoutnd);
180    fhBookTree->SetBranchAddress("Youtnd",Youtnd);    fhBookTree->SetBranchAddress("Youtnd",Youtnd);
181    fhBookTree->SetBranchAddress("Zoutnd",Zoutnd);    fhBookTree->SetBranchAddress("Zoutnd",Zoutnd);
182    fhBookTree->SetBranchAddress("Erelnd",Erelnd);    fhBookTree->SetBranchAddress("Erelnd",Erelnd);
183    fhBookTree->SetBranchAddress("Timend",Timend);    fhBookTree->SetBranchAddress("Timend",Timend);
184    fhBookTree->SetBranchAddress("Pathnd",Pathnd);    fhBookTree->SetBranchAddress("Pathnd",Pathnd);
185    fhBookTree->SetBranchAddress("P0nd",P0nd);    fhBookTree->SetBranchAddress("P0nd",P0nd);
186    fhBookTree->SetBranchAddress("Nthcard",&Nthcard);    fhBookTree->SetBranchAddress("Nthcard",&Nthcard);
187    fhBookTree->SetBranchAddress("Iparcard",Iparcard);    fhBookTree->SetBranchAddress("Iparcard",Iparcard);
188    fhBookTree->SetBranchAddress("Icard",Icard);    fhBookTree->SetBranchAddress("Icard",Icard);
189    fhBookTree->SetBranchAddress("Xincard",Xincard);    fhBookTree->SetBranchAddress("Xincard",Xincard);
190    fhBookTree->SetBranchAddress("Yincard",Yincard);    fhBookTree->SetBranchAddress("Yincard",Yincard);
191    fhBookTree->SetBranchAddress("Zincard",Zincard);    fhBookTree->SetBranchAddress("Zincard",Zincard);
192    fhBookTree->SetBranchAddress("Xoutcard",Xoutcard);    fhBookTree->SetBranchAddress("Xoutcard",Xoutcard);
193    fhBookTree->SetBranchAddress("Youtcard",Youtcard);    fhBookTree->SetBranchAddress("Youtcard",Youtcard);
194    fhBookTree->SetBranchAddress("Zoutcard",Zoutcard);    fhBookTree->SetBranchAddress("Zoutcard",Zoutcard);
195    fhBookTree->SetBranchAddress("Erelcard",Erelcard);    fhBookTree->SetBranchAddress("Erelcard",Erelcard);
196    fhBookTree->SetBranchAddress("Timecard",Timecard);    fhBookTree->SetBranchAddress("Timecard",Timecard);
197    fhBookTree->SetBranchAddress("Pathcard",Pathcard);    fhBookTree->SetBranchAddress("Pathcard",Pathcard);
198    fhBookTree->SetBranchAddress("P0card",P0card);    fhBookTree->SetBranchAddress("P0card",P0card);
199    
200    fhBookTree->SetBranchStatus("*",0);    fhBookTree->SetBranchStatus("*",0);
201    
202  };  };
203    
204    
205    
206  void Digitizer::Close(){  void Digitizer::Close(){
207    
208    delete fhBookTree;    delete fhBookTree;
209    
210  };  };
211    
212    
213    
214    
215  void Digitizer::Loop() {  void Digitizer::Loop() {
216    //    //
217    // opens the raw output file and loops over the events    // opens the raw output file and loops over the events
218    //    //
219    fOutputfile.open(fFilename, ios::out | ios::binary);    fOutputfile.open(fFilename, ios::out | ios::binary);
220    //fOutputfile.open(Form("Output%s",fFilename), ios::out | ios::binary);    //fOutputfile.open(Form("Output%s",fFilename), ios::out | ios::binary);
221    //    //
222    // Load in memory and save at the beginning of file the calorimeter calibration    // Load in memory and save at the beginning of file the calorimeter calibration
223    //    //
224    CaloLoadCalib();    CaloLoadCalib();
225    DigitizeCALOCALIB();    DigitizeCALOCALIB();
226    
227    //  load, digitize and write tracker calibration    //  load, digitize and write tracker calibration
228    LoadTrackCalib();    LoadTrackCalib();
229        
230    DigitizeTrackCalib(1);    DigitizeTrackCalib(1);
231    UInt_t length=fTracklength*2;    UInt_t length=fTracklength*2;
232    DigitizePSCU(length,0x12);    DigitizePSCU(length,0x12);
233    AddPadding();    AddPadding();
234    WriteTrackCalib();    WriteTrackCalib();
235        
236    DigitizeTrackCalib(2);    DigitizeTrackCalib(2);
237    length=fTracklength*2;    length=fTracklength*2;
238    DigitizePSCU(length,0x13);    DigitizePSCU(length,0x13);
239    AddPadding();    AddPadding();
240    WriteTrackCalib();    WriteTrackCalib();
241        
242    LoadMipCor();  // some initialization of parameters -not used now-    LoadMipCor();  // some initialization of parameters -not used now-
243    //  end loading, digitizing and writing tracker calibration    //  end loading, digitizing and writing tracker calibration
244    
245    //    //
246    // loops over the events    // loops over the events
247    //    //
248        
249    Int_t nentries = fhBookTree->GetEntriesFast();    Int_t nentries = fhBookTree->GetEntriesFast();
250    Long64_t nbytes = 0;    Long64_t nbytes = 0;
251    for (Int_t i=0; i<nentries;i++) {    for (Int_t i=0; i<nentries;i++) {
252      //      //
253      nbytes += fhBookTree->GetEntry(i);      nbytes += fhBookTree->GetEntry(i);
254      // read detectors sequentially:      // read detectors sequentially:
255      // http://www.ts.infn.it/fileadmin/documents/physics/experiments/wizard/cpu/gen_arch/RM_Acquisition.pdf      // http://www.ts.infn.it/fileadmin/documents/physics/experiments/wizard/cpu/gen_arch/RM_Acquisition.pdf
256      // on pamelatov:      // on pamelatov:
257      // /cvs/yoda/techmodel/physics/NeutronDetectorReader.cpp      // /cvs/yoda/techmodel/physics/NeutronDetectorReader.cpp
258      DigitizeTRIGGER();      DigitizeTRIGGER();
259      DigitizeTOF();      DigitizeTOF();
260      DigitizeAC();      DigitizeAC();
261      DigitizeCALO();      DigitizeCALO();
262      DigitizeTrack();      DigitizeTrack();
263      DigitizeS4();      DigitizeS4();
264      DigitizeND();      DigitizeND();
265        //        //
266      // Add padding to 64 bits      // Add padding to 64 bits
267      //      //
268      AddPadding();      AddPadding();
269  //  //
270      // Create CPU header, we need packet type (0x10 = physics data) and packet length.      // Create CPU header, we need packet type (0x10 = physics data) and packet length.
271      //      //
272      UInt_t length=2*(fCALOlength+fACbuffer+fTracklength+fNDbuffer+fS4buffer)+fPadding+fTOFbuffer+fTRIGGERbuffer;      UInt_t length=2*(fCALOlength+fACbuffer+fTracklength+fNDbuffer+fS4buffer)+fPadding+fTOFbuffer+fTRIGGERbuffer;
273      //UInt_t length=2*(fCALOlength+fACbuffer+fTracklength+fNDbuffer)+fPadding+fTOFbuffer+fTRIGGERbuffer;      //UInt_t length=2*(fCALOlength+fACbuffer+fTracklength+fNDbuffer)+fPadding+fTOFbuffer+fTRIGGERbuffer;
274      DigitizePSCU(length,0x10);      DigitizePSCU(length,0x10);
275      if ( !i%100 ) std::cout << "writing event " << i << endl;      if ( !i%100 ) std::cout << "writing event " << i << endl;
276      WriteData();      WriteData();
277    };    };
278    
279    fOutputfile.close();    fOutputfile.close();
280    std::cout << "files closed" << endl << flush;    std::cout << "files closed" << endl << flush;
281    
282  };  };
283    
284  void Digitizer::AddPadding(){  void Digitizer::AddPadding(){
285    //    //
286    Float_t pd0 = (fLen+16)/64.;    Float_t pd0 = (fLen+16)/64.;
287    Float_t pd1 = pd0 - (Float_t)int(pd0);    Float_t pd1 = pd0 - (Float_t)int(pd0);
288    Float_t padfrac = 64. - pd1 * 64.;    Float_t padfrac = 64. - pd1 * 64.;
289    //    //
290    UInt_t padbytes = (UInt_t)padfrac;    UInt_t padbytes = (UInt_t)padfrac;
291    if ( padbytes > 0 && padbytes < 64 ){    if ( padbytes > 0 && padbytes < 64 ){
292      //      //
293      // here the padding length      // here the padding length
294      //      //
295      fPadding = padbytes+64;      fPadding = padbytes+64;
296      //      //
297      // random padding bytes      // random padding bytes
298      //      //
299      for (Int_t ur=0; ur<32; ur++){      for (Int_t ur=0; ur<32; ur++){
300        fDataPadding[ur] = (UShort_t)rand();        fDataPadding[ur] = (UShort_t)rand();
301      };      };
302    };    };
303  };  };
304    
305    
306  void Digitizer::DigitizePSCU(UInt_t length, UChar_t type) {  void Digitizer::DigitizePSCU(UInt_t length, UChar_t type) {
307    //    //
308    UChar_t buff[16];    UChar_t buff[16];
309    //    //
310    // CPU signature    // CPU signature
311    //      //  
312    buff[0] = 0xFA;    buff[0] = 0xFA;
313    buff[1] = 0xFE;    buff[1] = 0xFE;
314    buff[2] = 0xDE;    buff[2] = 0xDE;
315    //    //
316    // packet type (twice)    // packet type (twice)
317    //    //
318    buff[3] = type;    buff[3] = type;
319    buff[4] = type;    buff[4] = type;
320    //    //
321    // counter    // counter
322    //    //
323    fCounter++;    fCounter++;
324    while ( fCounter > 16777215 ){    while ( fCounter > 16777215 ){
325      fCounter -= 16777215;      fCounter -= 16777215;
326    };    };
327    //    //
328    buff[5] = (UChar_t)(fCounter >> 16);    buff[5] = (UChar_t)(fCounter >> 16);
329    buff[6] = (UChar_t)(fCounter >> 8);    buff[6] = (UChar_t)(fCounter >> 8);
330    buff[7] = (UChar_t)fCounter;    buff[7] = (UChar_t)fCounter;
331    //    //
332    // on board time    // on board time
333    //    //
334    ULong64_t obt = fOBT + 30LL;    ULong64_t obt = fOBT + 30LL;
335    //    //
336    while ( obt > 4294967295LL ){    while ( obt > 4294967295LL ){
337      obt -= 4294967295LL;      obt -= 4294967295LL;
338    };    };
339    fOBT = (UInt_t)obt;    fOBT = (UInt_t)obt;
340    //    //
341    buff[8] = (UChar_t)(fOBT >> 24);    buff[8] = (UChar_t)(fOBT >> 24);
342    buff[9] = (UChar_t)(fOBT >> 16);    buff[9] = (UChar_t)(fOBT >> 16);
343    buff[10] = (UChar_t)(fOBT >> 8);    buff[10] = (UChar_t)(fOBT >> 8);
344    buff[11] = (UChar_t)fOBT;    buff[11] = (UChar_t)fOBT;
345    //    //
346    // Packet length    // Packet length
347    //    //
348    fLen = length;    fLen = length;
349    //    //
350    buff[12] = (UChar_t)(fLen >> 16);    buff[12] = (UChar_t)(fLen >> 16);
351    buff[13] = (UChar_t)(fLen >> 8);    buff[13] = (UChar_t)(fLen >> 8);
352    buff[14] = (UChar_t)fLen;    buff[14] = (UChar_t)fLen;
353    //    //
354    // CPU header CRC    // CPU header CRC
355    //    //
356    buff[15] = (BYTE)CM_Compute_CRC16((UINT16)0, (BYTE*)&buff, (UINT32)15);    buff[15] = (BYTE)CM_Compute_CRC16((UINT16)0, (BYTE*)&buff, (UINT32)15);
357    //    //
358    memcpy(fDataPSCU,buff,16*sizeof(UChar_t));    memcpy(fDataPSCU,buff,16*sizeof(UChar_t));
359    //    //
360  };  };
361    
362  void Digitizer::ClearCaloCalib(Int_t s){  void Digitizer::ClearCaloCalib(Int_t s){
363    //    //
364    fcstwerr[s] = 0;    fcstwerr[s] = 0;
365    fcperror[s] = 0.;    fcperror[s] = 0.;
366    for ( Int_t d=0 ; d<11 ;d++  ){    for ( Int_t d=0 ; d<11 ;d++  ){
367      Int_t pre = -1;      Int_t pre = -1;
368      for ( Int_t j=0; j<96 ;j++){      for ( Int_t j=0; j<96 ;j++){
369        if ( j%16 == 0 ) pre++;        if ( j%16 == 0 ) pre++;
370        fcalped[s][d][j] = 0.;        fcalped[s][d][j] = 0.;
371        fcstwerr[s] = 0.;        fcstwerr[s] = 0.;
372        fcperror[s] = 0.;        fcperror[s] = 0.;
373        fcalgood[s][d][j] = 0.;        fcalgood[s][d][j] = 0.;
374        fcalthr[s][d][pre] = 0.;        fcalthr[s][d][pre] = 0.;
375        fcalrms[s][d][j] = 0.;        fcalrms[s][d][j] = 0.;
376        fcalbase[s][d][pre] = 0.;        fcalbase[s][d][pre] = 0.;
377        fcalvar[s][d][pre] = 0.;        fcalvar[s][d][pre] = 0.;
378      };      };
379    };    };
380    return;    return;
381  }  }
382    
383  Int_t Digitizer::CaloLoadCalib(Int_t s,TString fcalname, UInt_t calibno){  Int_t Digitizer::CaloLoadCalib(Int_t s,TString fcalname, UInt_t calibno){
384    //    //
385    //    //
386    UInt_t e = 0;    UInt_t e = 0;
387    if ( s == 0 ) e = 0;    if ( s == 0 ) e = 0;
388    if ( s == 1 ) e = 2;    if ( s == 1 ) e = 2;
389    if ( s == 2 ) e = 3;    if ( s == 2 ) e = 3;
390    if ( s == 3 ) e = 1;    if ( s == 3 ) e = 1;
391    //    //
392    ifstream myfile;    ifstream myfile;
393    myfile.open(fcalname.Data());    myfile.open(fcalname.Data());
394    if ( !myfile ){        if ( !myfile ){    
395      return(-107);      return(-107);
396    };    };
397    myfile.close();    myfile.close();
398    //    //
399    TFile *File = new TFile(fcalname.Data());    TFile *File = new TFile(fcalname.Data());
400    if ( !File ) return(-108);    if ( !File ) return(-108);
401    TTree *tr = (TTree*)File->Get("CalibCalPed");    TTree *tr = (TTree*)File->Get("CalibCalPed");
402    if ( !tr ) return(-109);    if ( !tr ) return(-109);
403    //    //
404    TBranch *calo = tr->GetBranch("CalibCalPed");    TBranch *calo = tr->GetBranch("CalibCalPed");
405    //    //
406    pamela::CalibCalPedEvent *ce = 0;    pamela::CalibCalPedEvent *ce = 0;
407    tr->SetBranchAddress("CalibCalPed", &ce);    tr->SetBranchAddress("CalibCalPed", &ce);
408    //    //
409    Long64_t ncalibs = calo->GetEntries();    Long64_t ncalibs = calo->GetEntries();
410    //    //
411    if ( !ncalibs ) return(-110);    if ( !ncalibs ) return(-110);
412    //    //
413    calo->GetEntry(calibno);    calo->GetEntry(calibno);
414    //    //
415    if (ce->cstwerr[s] != 0 && ce->cperror[s] == 0 ) {    if (ce->cstwerr[s] != 0 && ce->cperror[s] == 0 ) {
416      fcstwerr[s] = ce->cstwerr[s];      fcstwerr[s] = ce->cstwerr[s];
417      fcperror[s] = ce->cperror[s];      fcperror[s] = ce->cperror[s];
418      for ( Int_t d=0 ; d<11 ;d++  ){      for ( Int_t d=0 ; d<11 ;d++  ){
419        Int_t pre = -1;        Int_t pre = -1;
420        for ( Int_t j=0; j<96 ;j++){        for ( Int_t j=0; j<96 ;j++){
421          if ( j%16 == 0 ) pre++;          if ( j%16 == 0 ) pre++;
422          fcalped[s][d][j] = ce->calped[e][d][j];          fcalped[s][d][j] = ce->calped[e][d][j];
423          fcalgood[s][d][j] = ce->calgood[e][d][j];          fcalgood[s][d][j] = ce->calgood[e][d][j];
424          fcalthr[s][d][pre] = ce->calthr[e][d][pre];          fcalthr[s][d][pre] = ce->calthr[e][d][pre];
425          fcalrms[s][d][j] = ce->calrms[e][d][j];          fcalrms[s][d][j] = ce->calrms[e][d][j];
426          fcalbase[s][d][pre] = ce->calbase[e][d][pre];          fcalbase[s][d][pre] = ce->calbase[e][d][pre];
427          fcalvar[s][d][pre] = ce->calvar[e][d][pre];          fcalvar[s][d][pre] = ce->calvar[e][d][pre];
428        };        };
429      };      };
430    } else {    } else {
431      printf(" CALORIMETER - ERROR: problems finding a good calibration in this file! \n\n ");      printf(" CALORIMETER - ERROR: problems finding a good calibration in this file! \n\n ");
432      File->Close();      File->Close();
433      return(-111);      return(-111);
434    };    };
435    File->Close();    File->Close();
436    return(0);    return(0);
437  }  }
438    
439    
440  void Digitizer::DigitizeCALOCALIB() {  void Digitizer::DigitizeCALOCALIB() {
441    //    //
442    // Header of the four sections    // Header of the four sections
443    //    //
444    fSecCalo[0] = 0xAA00; // XE    fSecCalo[0] = 0xAA00; // XE
445    fSecCalo[1] = 0xB100; // XO    fSecCalo[1] = 0xB100; // XO
446    fSecCalo[2] = 0xB600; // YE    fSecCalo[2] = 0xB600; // YE
447    fSecCalo[3] = 0xAD00; // YO    fSecCalo[3] = 0xAD00; // YO
448    //    //
449    // length of the data is 0x1215    // length of the data is 0x1215
450    //    //
451    fSecCALOLength[0] = 0x1215; // XE    fSecCALOLength[0] = 0x1215; // XE
452    fSecCALOLength[1] = 0x1215; // XO    fSecCALOLength[1] = 0x1215; // XO
453    fSecCALOLength[2] = 0x1215; // YE    fSecCALOLength[2] = 0x1215; // YE
454    fSecCALOLength[3] = 0x1215; // YO    fSecCALOLength[3] = 0x1215; // YO
455    //    //
456    Int_t chksum = 0;    Int_t chksum = 0;
457    UInt_t tstrip = 0;    UInt_t tstrip = 0;
458    UInt_t fSecPointer = 0;    UInt_t fSecPointer = 0;
459    //    //
460    for (Int_t sec=0; sec < 4; sec++){    for (Int_t sec=0; sec < 4; sec++){
461      //      //
462      // sec =    0 -> XE      1 -> XO        2-> YE         3 -> YO      // sec =    0 -> XE      1 -> XO        2-> YE         3 -> YO
463      //      //
464      fCALOlength = 0;      fCALOlength = 0;
465      memset(fDataCALO,0,sizeof(UShort_t)*fCALObuffer);      memset(fDataCALO,0,sizeof(UShort_t)*fCALObuffer);
466      fSecPointer = fCALOlength;      fSecPointer = fCALOlength;
467      //      //
468      // First of all we have section header and packet length      // First of all we have section header and packet length
469      //      //
470      fDataCALO[fCALOlength] = fSecCalo[sec];      fDataCALO[fCALOlength] = fSecCalo[sec];
471      fCALOlength++;      fCALOlength++;
472      fDataCALO[fCALOlength] = fSecCALOLength[sec];      fDataCALO[fCALOlength] = fSecCALOLength[sec];
473      fCALOlength++;      fCALOlength++;
474      //      //
475      // Section XO is read in the opposite direction respect to the others      // Section XO is read in the opposite direction respect to the others
476      //      //
477      chksum = 0;      chksum = 0;
478      //      //
479      for (Int_t plane=0; plane < 11; plane++){      for (Int_t plane=0; plane < 11; plane++){
480        //        //
481        if ( sec == 1 ) tstrip = fCALOlength + 96*2;        if ( sec == 1 ) tstrip = fCALOlength + 96*2;
482        //        //
483        for (Int_t strip=0; strip < 96; strip++){          for (Int_t strip=0; strip < 96; strip++){  
484          //          //
485          chksum += (Int_t)fcalped[sec][plane][strip];          chksum += (Int_t)fcalped[sec][plane][strip];
486          //          //
487          // save value          // save value
488          //          //
489          if ( sec == 1 ){          if ( sec == 1 ){
490            tstrip -= 2;            tstrip -= 2;
491            fDataCALO[tstrip] = (Int_t)fcalped[sec][plane][strip];            fDataCALO[tstrip] = (Int_t)fcalped[sec][plane][strip];
492            fDataCALO[tstrip+1] = (Int_t)fcalgood[sec][plane][strip];            fDataCALO[tstrip+1] = (Int_t)fcalgood[sec][plane][strip];
493          } else {          } else {
494            fDataCALO[fCALOlength] = (Int_t)fcalped[sec][plane][strip];            fDataCALO[fCALOlength] = (Int_t)fcalped[sec][plane][strip];
495            fDataCALO[fCALOlength+1] = (Int_t)fcalgood[sec][plane][strip];            fDataCALO[fCALOlength+1] = (Int_t)fcalgood[sec][plane][strip];
496          };          };
497          fCALOlength +=2;          fCALOlength +=2;
498        };        };
499        //        //
500      };      };
501      //      //
502      fDataCALO[fCALOlength] = (UShort_t)chksum;      fDataCALO[fCALOlength] = (UShort_t)chksum;
503      fCALOlength++;      fCALOlength++;
504      fDataCALO[fCALOlength] = 0;      fDataCALO[fCALOlength] = 0;
505      fCALOlength++;      fCALOlength++;
506      fDataCALO[fCALOlength] = (UShort_t)((Int_t)(chksum >> 16));      fDataCALO[fCALOlength] = (UShort_t)((Int_t)(chksum >> 16));
507      fCALOlength++;      fCALOlength++;
508      //      //
509      // Section XO is read in the opposite direction respect to the others      // Section XO is read in the opposite direction respect to the others
510      //      //
511      chksum = 0;      chksum = 0;
512      //      //
513      for (Int_t plane=0; plane < 11; plane++){      for (Int_t plane=0; plane < 11; plane++){
514        //        //
515        if ( sec == 1 ) tstrip = fCALOlength+6*2;        if ( sec == 1 ) tstrip = fCALOlength+6*2;
516        //        //
517        for (Int_t strip=0; strip < 6; strip++){        for (Int_t strip=0; strip < 6; strip++){
518          //          //
519          chksum += (Int_t)fcalthr[sec][plane][strip];          chksum += (Int_t)fcalthr[sec][plane][strip];
520          //          //
521          // save value          // save value
522          //          //
523          if ( sec == 1 ){          if ( sec == 1 ){
524            tstrip -= 2;            tstrip -= 2;
525            fDataCALO[tstrip] = 0;            fDataCALO[tstrip] = 0;
526            fDataCALO[tstrip+1] = (Int_t)fcalthr[sec][plane][strip];            fDataCALO[tstrip+1] = (Int_t)fcalthr[sec][plane][strip];
527          } else {          } else {
528            fDataCALO[fCALOlength] = 0;            fDataCALO[fCALOlength] = 0;
529            fDataCALO[fCALOlength+1] = (Int_t)fcalthr[sec][plane][strip];            fDataCALO[fCALOlength+1] = (Int_t)fcalthr[sec][plane][strip];
530          };          };
531          fCALOlength +=2;          fCALOlength +=2;
532        };        };
533        //        //
534      };      };
535      //      //
536      fDataCALO[fCALOlength] = 0;      fDataCALO[fCALOlength] = 0;
537      fCALOlength++;      fCALOlength++;
538      fDataCALO[fCALOlength] = (UShort_t)chksum;      fDataCALO[fCALOlength] = (UShort_t)chksum;
539      fCALOlength++;      fCALOlength++;
540      fDataCALO[fCALOlength] = 0;      fDataCALO[fCALOlength] = 0;
541      fCALOlength++;      fCALOlength++;
542      fDataCALO[fCALOlength] = (UShort_t)((Int_t)(chksum >> 16));      fDataCALO[fCALOlength] = (UShort_t)((Int_t)(chksum >> 16));
543      fCALOlength++;      fCALOlength++;
544      //      //
545      // Section XO is read in the opposite direction respect to the others      // Section XO is read in the opposite direction respect to the others
546      //      //
547      for (Int_t plane=0; plane < 11; plane++){      for (Int_t plane=0; plane < 11; plane++){
548        //        //
549        if ( sec == 1 ) tstrip = fCALOlength+96*2;        if ( sec == 1 ) tstrip = fCALOlength+96*2;
550        //        //
551        for (Int_t strip=0; strip < 96; strip++){        for (Int_t strip=0; strip < 96; strip++){
552          //          //
553          // save value          // save value
554          //          //
555          if ( sec == 1 ){          if ( sec == 1 ){
556            tstrip -= 2;            tstrip -= 2;
557            fDataCALO[tstrip] = 0;            fDataCALO[tstrip] = 0;
558            fDataCALO[tstrip+1] = (Int_t)fcalrms[sec][plane][strip];            fDataCALO[tstrip+1] = (Int_t)fcalrms[sec][plane][strip];
559          } else {          } else {
560            fDataCALO[fCALOlength] = 0;            fDataCALO[fCALOlength] = 0;
561            fDataCALO[fCALOlength+1] = (Int_t)fcalrms[sec][plane][strip];            fDataCALO[fCALOlength+1] = (Int_t)fcalrms[sec][plane][strip];
562          };          };
563          fCALOlength += 2;          fCALOlength += 2;
564        };        };
565        //        //
566      };          };    
567      //      //
568      // Section XO is read in the opposite direction respect to the others      // Section XO is read in the opposite direction respect to the others
569      //      //
570      for (Int_t plane=0; plane < 11; plane++){      for (Int_t plane=0; plane < 11; plane++){
571        //        //
572        if ( sec == 1 ) tstrip = fCALOlength+6*4;        if ( sec == 1 ) tstrip = fCALOlength+6*4;
573        //        //
574        for (Int_t strip=0; strip < 6; strip++){        for (Int_t strip=0; strip < 6; strip++){
575          //          //
576          // save value          // save value
577          //          //
578          if ( sec == 1 ){          if ( sec == 1 ){
579            tstrip -= 4;            tstrip -= 4;
580            fDataCALO[tstrip] = 0;            fDataCALO[tstrip] = 0;
581            fDataCALO[tstrip+1] = (Int_t)fcalbase[sec][plane][strip];            fDataCALO[tstrip+1] = (Int_t)fcalbase[sec][plane][strip];
582            fDataCALO[tstrip+2] = 0;            fDataCALO[tstrip+2] = 0;
583            fDataCALO[tstrip+3] = (Int_t)fcalvar[sec][plane][strip];            fDataCALO[tstrip+3] = (Int_t)fcalvar[sec][plane][strip];
584          } else {          } else {
585            fDataCALO[fCALOlength] = 0;            fDataCALO[fCALOlength] = 0;
586            fDataCALO[fCALOlength+1] = (Int_t)fcalbase[sec][plane][strip];            fDataCALO[fCALOlength+1] = (Int_t)fcalbase[sec][plane][strip];
587            fDataCALO[fCALOlength+2] = 0;            fDataCALO[fCALOlength+2] = 0;
588            fDataCALO[fCALOlength+3] = (Int_t)fcalvar[sec][plane][strip];            fDataCALO[fCALOlength+3] = (Int_t)fcalvar[sec][plane][strip];
589          };          };
590          fCALOlength +=4;          fCALOlength +=4;
591        };        };
592        //        //
593      };            };      
594      //      //
595      //      //
596      // here we calculate and save the CRC      // here we calculate and save the CRC
597      //      //
598      fDataCALO[fCALOlength] = 0;      fDataCALO[fCALOlength] = 0;
599      fCALOlength++;      fCALOlength++;
600      Short_t CRC = 0;      Short_t CRC = 0;
601      for (UInt_t i=0; i<(fCALOlength-fSecPointer); i++){      for (UInt_t i=0; i<(fCALOlength-fSecPointer); i++){
602        CRC=crc(CRC,fDataCALO[i+fSecPointer]);        CRC=crc(CRC,fDataCALO[i+fSecPointer]);
603      };      };
604      fDataCALO[fCALOlength] = (UShort_t)CRC;      fDataCALO[fCALOlength] = (UShort_t)CRC;
605      fCALOlength++;      fCALOlength++;
606      //      //
607      UInt_t length=fCALOlength*2;      UInt_t length=fCALOlength*2;
608      DigitizePSCU(length,0x18);      DigitizePSCU(length,0x18);
609      //      //
610      // Add padding to 64 bits      // Add padding to 64 bits
611      //      //
612      AddPadding();      AddPadding();
613      //      //
614      fOutputfile.write(reinterpret_cast<char*>(fDataPSCU),sizeof(UShort_t)*fPSCUbuffer);      fOutputfile.write(reinterpret_cast<char*>(fDataPSCU),sizeof(UShort_t)*fPSCUbuffer);
615      UShort_t temp[1000000];      UShort_t temp[1000000];
616      memset(temp,0,sizeof(UShort_t)*1000000);      memset(temp,0,sizeof(UShort_t)*1000000);
617      swab(fDataCALO,temp,sizeof(UShort_t)*fCALOlength);  // WE MUST SWAP THE BYTES!!!      swab(fDataCALO,temp,sizeof(UShort_t)*fCALOlength);  // WE MUST SWAP THE BYTES!!!
618      fOutputfile.write(reinterpret_cast<char*>(temp),sizeof(UShort_t)*fCALOlength);      fOutputfile.write(reinterpret_cast<char*>(temp),sizeof(UShort_t)*fCALOlength);
619      //      //
620      // padding to 64 bytes      // padding to 64 bytes
621      //      //
622      if ( fPadding ){      if ( fPadding ){
623        fOutputfile.write(reinterpret_cast<char*>(fDataPadding),sizeof(UChar_t)*fPadding);        fOutputfile.write(reinterpret_cast<char*>(fDataPadding),sizeof(UChar_t)*fPadding);
624      };      };
625      //      //
626      //          //    
627    };    };
628    //    //
629  };  };
630    
631  void Digitizer::CaloLoadCalib() {  void Digitizer::CaloLoadCalib() {
632    //    //
633    fGivenCaloCalib = 0; //                                  ####@@@@ should be given as input par @@@@####    fGivenCaloCalib = 0; //                                  ####@@@@ should be given as input par @@@@####
634    //    //
635    // first of all load the MIP to ADC conversion values    // first of all load the MIP to ADC conversion values
636    //    //
637    stringstream calfile;    stringstream calfile;
638    Int_t error = 0;    Int_t error = 0;
639    GL_PARAM *glparam = new GL_PARAM();    GL_PARAM *glparam = new GL_PARAM();
640    //    //
641    // determine where I can find calorimeter ADC to MIP conversion file      // determine where I can find calorimeter ADC to MIP conversion file  
642    //    //
643    error = 0;    error = 0;
644    error = glparam->Query_GL_PARAM(3,101,fDbc);    error = glparam->Query_GL_PARAM(3,101,fDbc);
645    //    //
646    calfile.str("");    calfile.str("");
647    calfile << glparam->PATH.Data() << "/";    calfile << glparam->PATH.Data() << "/";
648    calfile << glparam->NAME.Data();    calfile << glparam->NAME.Data();
649    //    //
650    printf("\n Using Calorimeter ADC to MIP conversion file: \n %s \n",calfile.str().c_str());    printf("\n Using Calorimeter ADC to MIP conversion file: \n %s \n",calfile.str().c_str());
651    FILE *f;    FILE *f;
652    f = fopen(calfile.str().c_str(),"rb");    f = fopen(calfile.str().c_str(),"rb");
653    //    //
654    memset(fCalomip,0,4224*sizeof(fCalomip[0][0][0]));    memset(fCalomip,0,4224*sizeof(fCalomip[0][0][0]));
655    //    //
656    for (Int_t m = 0; m < 2 ; m++ ){    for (Int_t m = 0; m < 2 ; m++ ){
657      for (Int_t k = 0; k < 22; k++ ){      for (Int_t k = 0; k < 22; k++ ){
658        for (Int_t l = 0; l < 96; l++ ){        for (Int_t l = 0; l < 96; l++ ){
659          fread(&fCalomip[m][k][l],sizeof(fCalomip[m][k][l]),1,f);          fread(&fCalomip[m][k][l],sizeof(fCalomip[m][k][l]),1,f);
660        };        };
661      };      };
662    };    };
663    fclose(f);    fclose(f);
664    //    //
665    // determine which calibration has to be used and load it for each section    // determine which calibration has to be used and load it for each section
666    //      //  
667    GL_CALO_CALIB *glcalo = new GL_CALO_CALIB();    GL_CALO_CALIB *glcalo = new GL_CALO_CALIB();
668    GL_ROOT *glroot = new GL_ROOT();      GL_ROOT *glroot = new GL_ROOT();  
669    TString fcalname;    TString fcalname;
670    UInt_t idcalib;    UInt_t idcalib;
671    UInt_t calibno;    UInt_t calibno;
672    UInt_t utime = 0;    UInt_t utime = 0;
673    //    //
674    for (UInt_t s=0; s<4; s++){    for (UInt_t s=0; s<4; s++){
675      //      //
676      // clear calo calib variables for section s      // clear calo calib variables for section s
677      //      //
678      ClearCaloCalib(s);      ClearCaloCalib(s);
679      //      //
680      if ( fGivenCaloCalib ){      if ( fGivenCaloCalib ){
681        //        //
682        // a time has been given as input on the command line so retrieve the calibration that preceed that time        // a time has been given as input on the command line so retrieve the calibration that preceed that time
683        //        //
684        glcalo->Query_GL_CALO_CALIB(fGivenCaloCalib,utime,s,fDbc);        glcalo->Query_GL_CALO_CALIB(fGivenCaloCalib,utime,s,fDbc);
685        //          //  
686        calibno = glcalo->EV_ROOT;        calibno = glcalo->EV_ROOT;
687        idcalib = glcalo->ID_ROOT_L0;        idcalib = glcalo->ID_ROOT_L0;
688        //        //
689        // determine path and name and entry of the calibration file        // determine path and name and entry of the calibration file
690        //        //
691        printf("\n");        printf("\n");
692        printf(" ** SECTION %i **\n",s);        printf(" ** SECTION %i **\n",s);
693        //        //
694        glroot->Query_GL_ROOT(idcalib,fDbc);        glroot->Query_GL_ROOT(idcalib,fDbc);
695        //        //
696        stringstream name;        stringstream name;
697        name.str("");        name.str("");
698        name << glroot->PATH.Data() << "/";        name << glroot->PATH.Data() << "/";
699        name << glroot->NAME.Data();        name << glroot->NAME.Data();
700        //        //
701        fcalname = (TString)name.str().c_str();        fcalname = (TString)name.str().c_str();
702        //        //
703        printf("\n Section %i : using  file %s calibration at entry %i: \n",s,fcalname.Data(),calibno);        printf("\n Section %i : using  file %s calibration at entry %i: \n",s,fcalname.Data(),calibno);
704        //        //
705      } else {      } else {
706        error = 0;        error = 0;
707        error = glparam->Query_GL_PARAM(1,104,fDbc);        error = glparam->Query_GL_PARAM(1,104,fDbc);
708        //        //
709        calfile.str("");        calfile.str("");
710        calfile << glparam->PATH.Data() << "/";        calfile << glparam->PATH.Data() << "/";
711        calfile << glparam->NAME.Data();        calfile << glparam->NAME.Data();
712        //        //
713        printf("\n Section %i : using default calorimeter calibration: \n %s \n",s,calfile.str().c_str());        printf("\n Section %i : using default calorimeter calibration: \n %s \n",s,calfile.str().c_str());
714        //        //
715        fcalname = (TString)calfile.str().c_str();        fcalname = (TString)calfile.str().c_str();
716        calibno = s;        calibno = s;
717        //        //
718      };      };
719      //      //
720      // load calibration variables in memory      // load calibration variables in memory
721      //      //
722      CaloLoadCalib(s,fcalname,calibno);      CaloLoadCalib(s,fcalname,calibno);
723      //      //
724    };    };
725    //    //
726    // at this point we have in memory the calorimeter calibration and we can save it to disk in the correct format and use it to digitize the data    // at this point we have in memory the calorimeter calibration and we can save it to disk in the correct format and use it to digitize the data
727    //    //
728    delete glparam;    delete glparam;
729    delete glcalo;    delete glcalo;
730    delete glroot;    delete glroot;
731  };  };
732    
733  void Digitizer::DigitizeCALO() {  void Digitizer::DigitizeCALO() {
734    //    //
735    fModCalo = 0; // 0 is RAW, 1 is COMPRESS, 2 is FULL     ####@@@@ should be given as input par @@@@####    fModCalo = 0; // 0 is RAW, 1 is COMPRESS, 2 is FULL     ####@@@@ should be given as input par @@@@####
736    //    //
737    //    //
738    //    //
739    fCALOlength = 0;  // reset total dimension of calo data    fCALOlength = 0;  // reset total dimension of calo data
740    //    //
741    // gpamela variables to be used    // gpamela variables to be used
742    //    //
743    fhBookTree->SetBranchStatus("Nthcali",1);    fhBookTree->SetBranchStatus("Nthcali",1);
744    fhBookTree->SetBranchStatus("Icaplane",1);    fhBookTree->SetBranchStatus("Icaplane",1);
745    fhBookTree->SetBranchStatus("Icastrip",1);    fhBookTree->SetBranchStatus("Icastrip",1);
746    fhBookTree->SetBranchStatus("Icamod",1);    fhBookTree->SetBranchStatus("Icamod",1);
747    fhBookTree->SetBranchStatus("Enestrip",1);    fhBookTree->SetBranchStatus("Enestrip",1);
748    //    //
749    // call different routines depending on the acq mode you want to simulate    // call different routines depending on the acq mode you want to simulate
750    //    //
751    switch ( fModCalo ){    switch ( fModCalo ){
752    case 0:    case 0:
753      this->DigitizeCALORAW();      this->DigitizeCALORAW();
754      break;      break;
755    case 1:    case 1:
756      this->DigitizeCALOCOMPRESS();      this->DigitizeCALOCOMPRESS();
757      break;      break;
758    case 2:    case 2:
759      this->DigitizeCALOFULL();      this->DigitizeCALOFULL();
760      break;      break;
761    };    };
762    //    //
763  };  };
764    
765  Float_t Digitizer::GetCALOen(Int_t sec, Int_t plane, Int_t strip){  Float_t Digitizer::GetCALOen(Int_t sec, Int_t plane, Int_t strip){
766    //    //
767    // determine plane and strip    // determine plane and strip
768    //    //
769    Int_t mplane = 0;    Int_t mplane = 0;
770    //    //
771    // wrong!    // wrong!
772    //    //
773    //  if ( sec == 0 || sec == 3 ) mplane = (plane * 4) + sec + 1;      //  if ( sec == 0 || sec == 3 ) mplane = (plane * 4) + sec + 1;  
774    //  if ( sec == 1 ) mplane = (plane * 4) + 2 + 1;      //  if ( sec == 1 ) mplane = (plane * 4) + 2 + 1;  
775    //  if ( sec == 2 ) mplane = (plane * 4) + 1 + 1;      //  if ( sec == 2 ) mplane = (plane * 4) + 1 + 1;  
776    //    //
777    if ( sec == 0 ) mplane = plane * 4 + 1; // it must be 0, 4, 8, ... (+1)  from plane = 0, 11    if ( sec == 0 ) mplane = plane * 4 + 1; // it must be 0, 4, 8, ... (+1)  from plane = 0, 11
778    if ( sec == 1 ) mplane = plane * 4 + 2 + 1; // it must be 2, 6, 10, ... (+1)  from plane = 0, 11    if ( sec == 1 ) mplane = plane * 4 + 2 + 1; // it must be 2, 6, 10, ... (+1)  from plane = 0, 11
779    if ( sec == 2 ) mplane = plane * 4 + 3 + 1; // it must be 3, 7, 11, ... (+1)  from plane = 0, 11    if ( sec == 2 ) mplane = plane * 4 + 3 + 1; // it must be 3, 7, 11, ... (+1)  from plane = 0, 11
780    if ( sec == 3 ) mplane = plane * 4 + 1 + 1; // it must be 1, 5, 9, ... (+1)  from plane = 0, 11    if ( sec == 3 ) mplane = plane * 4 + 1 + 1; // it must be 1, 5, 9, ... (+1)  from plane = 0, 11
781    //    //
782    Int_t mstrip = strip + 1;    Int_t mstrip = strip + 1;
783    //    //
784    // search energy release in gpamela output    // search energy release in gpamela output
785    //    //
786    for (Int_t i=0; i<Nthcali;i++){    for (Int_t i=0; i<Nthcali;i++){
787      if ( Icaplane[i] == mplane && Icastrip[i] == mstrip ){      if ( Icaplane[i] == mplane && Icastrip[i] == mstrip ){
788        return (Enestrip[i]);        return (Enestrip[i]);
789      };      };
790    };    };
791    //    //
792    // if not found it means no energy release so return 0.    // if not found it means no energy release so return 0.
793    //    //
794    return(0.);    return(0.);
795  };  };
796    
797  void Digitizer::DigitizeCALORAW() {  void Digitizer::DigitizeCALORAW() {
798    //    //
799    // some variables    // some variables
800    //    //
801    Float_t ens = 0.;    Float_t ens = 0.;
802    UInt_t adcsig = 0;    UInt_t adcsig = 0;
803    UInt_t adcbase = 0;    UInt_t adcbase = 0;
804    UInt_t adc = 0;    UInt_t adc = 0;
805    Int_t pre = 0;    Int_t pre = 0;
806    UInt_t l = 0;    UInt_t l = 0;
807    UInt_t lpl = 0;    UInt_t lpl = 0;
808    UInt_t tstrip = 0;    UInt_t tstrip = 0;
809    UInt_t fSecPointer = 0;    UInt_t fSecPointer = 0;
810    Double_t pedenoise;    Double_t pedenoise;
811    Float_t rms = 0.;    Float_t rms = 0.;
812    Float_t pedestal = 0.;    Float_t pedestal = 0.;
813    //    //
814    // clean the data structure    // clean the data structure
815    //    //
816    memset(fDataCALO,0,sizeof(UShort_t)*fCALObuffer);    memset(fDataCALO,0,sizeof(UShort_t)*fCALObuffer);
817    //    //
818    // Header of the four sections    // Header of the four sections
819    //    //
820    fSecCalo[0] = 0xEA08; // XE    fSecCalo[0] = 0xEA08; // XE
821    fSecCalo[1] = 0xF108; // XO    fSecCalo[1] = 0xF108; // XO
822    fSecCalo[2] = 0xF608; // YE    fSecCalo[2] = 0xF608; // YE
823    fSecCalo[3] = 0xED08; // YO    fSecCalo[3] = 0xED08; // YO
824    //    //
825    // length of the data is 0x0428 in RAW mode    // length of the data is 0x0428 in RAW mode
826    //    //
827    fSecCALOLength[0] = 0x0428; // XE    fSecCALOLength[0] = 0x0428; // XE
828    fSecCALOLength[1] = 0x0428; // XO    fSecCALOLength[1] = 0x0428; // XO
829    fSecCALOLength[2] = 0x0428; // YE    fSecCALOLength[2] = 0x0428; // YE
830    fSecCALOLength[3] = 0x0428; // YO    fSecCALOLength[3] = 0x0428; // YO
831    //    //
832    // let's start    // let's start
833    //    //
834    fCALOlength = 0;    fCALOlength = 0;
835    //    //
836    for (Int_t sec=0; sec < 4; sec++){    for (Int_t sec=0; sec < 4; sec++){
837      //      //
838      // sec =    0 -> XE      1 -> XO        2-> YE         3 -> YO      // sec =    0 -> XE      1 -> XO        2-> YE         3 -> YO
839      //      //
840      l = 0;                 // XE and XO are Y planes      l = 0;                 // XE and XO are Y planes
841      if ( sec < 2 ) l = 1;  // while YE and  YO are X planes      if ( sec < 2 ) l = 1;  // while YE and  YO are X planes
842      //      //
843      fSecPointer = fCALOlength;      fSecPointer = fCALOlength;
844      //      //
845      // First of all we have section header and packet length      // First of all we have section header and packet length
846      //      //
847      fDataCALO[fCALOlength] = fSecCalo[sec];      fDataCALO[fCALOlength] = fSecCalo[sec];
848      fCALOlength++;      fCALOlength++;
849      fDataCALO[fCALOlength] = fSecCALOLength[sec];      fDataCALO[fCALOlength] = fSecCALOLength[sec];
850      fCALOlength++;      fCALOlength++;
851      //      //
852      // selftrigger coincidences - in the future we should add here some code to simulate timing response of pre-amplifiers      // selftrigger coincidences - in the future we should add here some code to simulate timing response of pre-amplifiers
853      //      //
854      for (Int_t autoplane=0; autoplane < 7; autoplane++){      for (Int_t autoplane=0; autoplane < 7; autoplane++){
855        fDataCALO[fCALOlength] = 0x0000;        fDataCALO[fCALOlength] = 0x0000;
856        fCALOlength++;        fCALOlength++;
857      };      };
858      //      //
859      //      //
860      // here comes data      // here comes data
861      //      //
862      //      //
863      // Section XO is read in the opposite direction respect to the others      // Section XO is read in the opposite direction respect to the others
864      //      //
865      if ( sec == 1 ){            if ( sec == 1 ){      
866        tstrip = 96*11 + fCALOlength;        tstrip = 96*11 + fCALOlength;
867      } else {      } else {
868        tstrip = 0;        tstrip = 0;
869      };      };
870      //      //
871      pre = -1;      pre = -1;
872      //      //
873      for (Int_t strip=0; strip < 96; strip++){        for (Int_t strip=0; strip < 96; strip++){  
874        //        //
875        // which is the pre for this strip?        // which is the pre for this strip?
876        //        //
877        if (strip%16 == 0) {        if (strip%16 == 0) {
878          pre++;          pre++;
879        };        };
880        //        //
881        if ( sec == 1 ) tstrip -= 11;        if ( sec == 1 ) tstrip -= 11;
882        //        //
883        for (Int_t plane=0; plane < 11; plane++){        for (Int_t plane=0; plane < 11; plane++){
884          //          //
885          // here is wrong!!!!          // here is wrong!!!!
886          //          //
887          //          //
888          //      if ( plane%2 == 0 && sec%2 != 0){          //      if ( plane%2 == 0 && sec%2 != 0){
889          //        lpl = plane*2;          //        lpl = plane*2;
890          //      } else {          //      } else {
891          //        lpl = (plane*2) + 1;          //        lpl = (plane*2) + 1;
892          //      };          //      };
893          //          //
894          if ( sec == 0 || sec == 3 ) lpl = plane * 2;          if ( sec == 0 || sec == 3 ) lpl = plane * 2;
895          if ( sec == 1 || sec == 2 ) lpl = (plane * 2) + 1;          if ( sec == 1 || sec == 2 ) lpl = (plane * 2) + 1;
896          //          //
897          // get the energy in GeV from the simulation for that strip          // get the energy in GeV from the simulation for that strip
898          //          //
899          ens = this->GetCALOen(sec,plane,strip);          ens = this->GetCALOen(sec,plane,strip);
900          //          //
901          // convert it into ADC channels          // convert it into ADC channels
902          //                //      
903          adcsig = int(ens*fCalomip[l][lpl][strip]/fCALOGeV2MIPratio);          adcsig = int(ens*fCalomip[l][lpl][strip]/fCALOGeV2MIPratio);
904          //          //
905          // sum baselines          // sum baselines
906          //          //
907          adcbase = (UInt_t)fcalbase[sec][plane][pre];          adcbase = (UInt_t)fcalbase[sec][plane][pre];
908          //          //
909          // add noise and pedestals          // add noise and pedestals
910          //                //      
911          pedestal = fcalped[sec][plane][strip];          pedestal = fcalped[sec][plane][strip];
912          rms = fcalrms[sec][plane][strip]/4.;          rms = fcalrms[sec][plane][strip]/4.;
913          //          //
914          // Add random gaussian noise of RMS rms and Centered in the pedestal          // Add random gaussian noise of RMS rms and Centered in the pedestal
915          //          //
916          pedenoise = gRandom->Gaus((Double_t)pedestal,(Double_t)rms);          pedenoise = gRandom->Gaus((Double_t)pedestal,(Double_t)rms);
917          //          //
918          // Sum all contribution          // Sum all contribution
919          //          //
920          adc = adcsig + adcbase + (Int_t)round(pedenoise);          adc = adcsig + adcbase + (Int_t)round(pedenoise);
921          //          //
922          // Signal saturation          // Signal saturation
923          //          //
924          if ( adc > 0x7FFF ) adc = 0x7FFF;          if ( adc > 0x7FFF ) adc = 0x7FFF;
925          //          //
926          // save value          // save value
927          //          //
928          if ( sec == 1 ){          if ( sec == 1 ){
929            fDataCALO[tstrip] = adc;            fDataCALO[tstrip] = adc;
930            tstrip++;            tstrip++;
931          } else {          } else {
932            fDataCALO[fCALOlength] = adc;            fDataCALO[fCALOlength] = adc;
933          };          };
934          fCALOlength++;          fCALOlength++;
935          //          //
936        };        };
937        //        //
938        if ( sec == 1 ) tstrip -= 11;        if ( sec == 1 ) tstrip -= 11;
939        //        //
940      };      };
941      //      //
942      // here we calculate and save the CRC      // here we calculate and save the CRC
943      //      //
944      Short_t CRC = 0;      Short_t CRC = 0;
945      for (UInt_t i=0; i<(fCALOlength-fSecPointer); i++){      for (UInt_t i=0; i<(fCALOlength-fSecPointer); i++){
946        CRC=crc(CRC,fDataCALO[i+fSecPointer]);        CRC=crc(CRC,fDataCALO[i+fSecPointer]);
947      };      };
948      fDataCALO[fCALOlength] = (UShort_t)CRC;      fDataCALO[fCALOlength] = (UShort_t)CRC;
949      fCALOlength++;      fCALOlength++;
950      //      //
951    };    };
952    //    //
953    //   for (Int_t i=0; i<fCALOlength; i++){    //   for (Int_t i=0; i<fCALOlength; i++){
954    //     printf(" WORD %i       DIGIT %0x   \n",i,fDataCALO[i]);    //     printf(" WORD %i       DIGIT %0x   \n",i,fDataCALO[i]);
955    //   };    //   };
956    //    //
957  };  };
958    
959  void Digitizer::DigitizeCALOCOMPRESS() {  void Digitizer::DigitizeCALOCOMPRESS() {
960    //    //
961    printf(" COMPRESS MODE STILL NOT IMPLEMENTED! \n");      printf(" COMPRESS MODE STILL NOT IMPLEMENTED! \n");  
962    //    //
963    this->DigitizeCALORAW();    this->DigitizeCALORAW();
964    return;    return;
965    //    //
966    //    //
967    //    //
968    fSecCalo[0] = 0xEA00;    fSecCalo[0] = 0xEA00;
969    fSecCalo[1] = 0xF100;    fSecCalo[1] = 0xF100;
970    fSecCalo[2] = 0xF600;    fSecCalo[2] = 0xF600;
971    fSecCalo[3] = 0xED00;    fSecCalo[3] = 0xED00;
972    //    //
973    // length of the data in DSP mode must be calculated on fly during digitization    // length of the data in DSP mode must be calculated on fly during digitization
974    //    //
975    memset(fSecCALOLength,0x0,4*sizeof(UShort_t));    memset(fSecCALOLength,0x0,4*sizeof(UShort_t));
976    //    //
977    // here comes raw data    // here comes raw data
978    //    //
979    Int_t en = 0;    Int_t en = 0;
980    //    //
981    for (Int_t sec=0; sec < 4; sec++){    for (Int_t sec=0; sec < 4; sec++){
982      fDataCALO[en] = fSecCalo[sec];      fDataCALO[en] = fSecCalo[sec];
983      en++;      en++;
984      fDataCALO[en] = fSecCALOLength[sec];      fDataCALO[en] = fSecCALOLength[sec];
985      en++;      en++;
986      for (Int_t plane=0; plane < 11; plane++){      for (Int_t plane=0; plane < 11; plane++){
987        for (Int_t strip=0; strip < 11; strip++){        for (Int_t strip=0; strip < 11; strip++){
988          fDataCALO[en] = 0x0;          fDataCALO[en] = 0x0;
989          en++;          en++;
990        };        };
991      };      };
992    };    };
993    //    //
994  };  };
995    
996  void Digitizer::DigitizeCALOFULL() {  void Digitizer::DigitizeCALOFULL() {
997    //    //
998    printf(" FULL MODE STILL NOT IMPLEMENTED! \n");      printf(" FULL MODE STILL NOT IMPLEMENTED! \n");  
999    //    //
1000    this->DigitizeCALORAW();    this->DigitizeCALORAW();
1001    return;    return;
1002    //    //
1003    fSecCalo[0] = 0xEA00;    fSecCalo[0] = 0xEA00;
1004    fSecCalo[1] = 0xF100;    fSecCalo[1] = 0xF100;
1005    fSecCalo[2] = 0xF600;    fSecCalo[2] = 0xF600;
1006    fSecCalo[3] = 0xED00;    fSecCalo[3] = 0xED00;
1007    //    //
1008    // length of the data in DSP mode must be calculated on fly during digitization    // length of the data in DSP mode must be calculated on fly during digitization
1009    //    //
1010    memset(fSecCALOLength,0x0,4*sizeof(UShort_t));    memset(fSecCALOLength,0x0,4*sizeof(UShort_t));
1011    //    //
1012    // here comes raw data    // here comes raw data
1013    //    //
1014    Int_t  en = 0;    Int_t  en = 0;
1015    //    //
1016    for (Int_t sec=0; sec < 4; sec++){    for (Int_t sec=0; sec < 4; sec++){
1017      fDataCALO[en] = fSecCalo[sec];      fDataCALO[en] = fSecCalo[sec];
1018      en++;      en++;
1019      fDataCALO[en] = fSecCALOLength[sec];      fDataCALO[en] = fSecCALOLength[sec];
1020      en++;      en++;
1021      for (Int_t plane=0; plane < 11; plane++){      for (Int_t plane=0; plane < 11; plane++){
1022        for (Int_t strip=0; strip < 11; strip++){        for (Int_t strip=0; strip < 11; strip++){
1023          fDataCALO[en] = 0x0;          fDataCALO[en] = 0x0;
1024          en++;          en++;
1025        };        };
1026      };      };
1027    };    };
1028    //    //
1029  };  };
1030    
1031  void Digitizer::DigitizeTRIGGER() {  void Digitizer::DigitizeTRIGGER() {
1032    //fDataTrigger: 153 bytes    //fDataTrigger: 153 bytes
1033    for (Int_t j=0; j < 153; j++)    for (Int_t j=0; j < 153; j++)
1034      fDataTrigger[0]=0x00;      fDataTrigger[j]=0x00;
1035  };  };
1036    
1037  Int_t Digitizer::DigitizeTOF() {  Int_t Digitizer::DigitizeTOF() {
1038    //fDataTof: 12 x 23 bytes (=276 bytes)    //fDataTof: 12 x 23 bytes (=276 bytes)
1039    UChar_t *pTof=fDataTof;    UChar_t *pTof=fDataTof;
1040    Bool_t DEBUG=false;    Bool_t DEBUG=false;
1041    
1042    // --- activate branches:    // --- activate branches:
1043    fhBookTree->SetBranchStatus("Nthtof",1);    fhBookTree->SetBranchStatus("Nthtof",1);
1044    fhBookTree->SetBranchStatus("Ipltof",1);    fhBookTree->SetBranchStatus("Ipltof",1);
1045    fhBookTree->SetBranchStatus("Ipaddle",1);    fhBookTree->SetBranchStatus("Ipaddle",1);
1046    fhBookTree->SetBranchStatus("Xintof",1);    fhBookTree->SetBranchStatus("Xintof",1);
1047    fhBookTree->SetBranchStatus("Yintof",1);    fhBookTree->SetBranchStatus("Yintof",1);
1048    fhBookTree->SetBranchStatus("Xouttof",1);    fhBookTree->SetBranchStatus("Xouttof",1);
1049    fhBookTree->SetBranchStatus("Youttof",1);    fhBookTree->SetBranchStatus("Youttof",1);
1050    fhBookTree->SetBranchStatus("Ereltof",1);    fhBookTree->SetBranchStatus("Ereltof",1);
1051    fhBookTree->SetBranchStatus("Timetof",1);    fhBookTree->SetBranchStatus("Timetof",1);
1052    // not yet used: Zintof, Xouttof, Youttof, Zouttof    // not yet used: Zintof, Xouttof, Youttof, Zouttof
1053    
1054    // ------ evaluate energy in each pmt: ------    // ------ evaluate energy in each pmt: ------
1055    // strip geometry (lenght/width)    // strip geometry (lenght/width)
1056    Float_t dimel[6] = {33.0, 40.8 ,18.0, 15.0, 15.0, 18.0};    Float_t dimel[6] = {33.0, 40.8 ,18.0, 15.0, 15.0, 18.0};
1057    //Float_t dimes[6] = {5.1, 5.5, 7.5, 9.0, 6.0, 5.0};    //Float_t dimes[6] = {5.1, 5.5, 7.5, 9.0, 6.0, 5.0};
1058        
1059    //  S11 8 paddles  33.0 x 5.1 cm    //  S11 8 paddles  33.0 x 5.1 cm
1060    //  S12 6 paddles  40.8 x 5.5 cm    //  S12 6 paddles  40.8 x 5.5 cm
1061    //  S21 2 paddles  18.0 x 7.5 cm    //  S21 2 paddles  18.0 x 7.5 cm
1062    //  S22 2 paddles  15.0 x 9.0 cm    //  S22 2 paddles  15.0 x 9.0 cm
1063    //  S31 3 paddles  15.0 x 6.0 cm    //  S31 3 paddles  15.0 x 6.0 cm
1064    //  S32 3 paddles  18.0 x 5.0 cm    //  S32 3 paddles  18.0 x 5.0 cm
1065    
1066    // distance from the interaction point to the pmts (right,left)    Float_t FGeo[2]={0., 0.}; /* geometrical factor */
1067    Float_t xpath[2]={0., 0.}; /*path(cm) in X per S12,S21,S32 verso il pmt DX o SX*/  
1068    Float_t ypath[2]={0., 0.}; /*path(cm) in Y per S11,S22,S31 verso il pmt DX o SX*/    const Float_t Pho_keV = 10.;     // photons per keV in scintillator
1069    Float_t FGeo[2]={0., 0.}; /* fattore geometrico */    const Float_t echarge = 1.6e-19; // electron charge
1070      Float_t Npho=0.;
1071    const Float_t Pho_keV = 10.;     // photons per keV in scintillator    Float_t QevePmt_pC[48];
1072    const Float_t echarge = 1.6e-19; // carica dell'elettrone    Float_t QhitPad_pC[2]={0., 0.};
1073    Float_t Npho=0.;    Float_t QhitPmt_pC[2]={0., 0.};
1074    Float_t QevePmt_pC[48];    Float_t pmGain = 3.5e6;  /* PMT Gain: the same for all PMTs */
1075    Float_t QhitPad_pC[2]={0., 0.};    Float_t effi=0.21;       /* Efficienza di fotocatodo */
1076    Float_t QhitPmt_pC[2]={0., 0.};  
1077    Float_t pmGain = 3.5e6;  /* Gain: per il momento uguale per tutti */    //   Float_t ADC_pC0=-58.1;      //  ADC/pC conversion coefficient 0
1078    Float_t effi=0.21;       /* Efficienza di fotocatodo */    //   Float_t ADC_pC1=1.728;      //  ADC/pC conversion coefficient 1
1079    Float_t ADC_pC=1.666667; // ADC_ch/pC conversion = 0.6 pC/channel (+30 di offset)    //   Float_t ADC_pC2=-4.063e-05; //  ADC/pC conversion coefficient 2
1080    Float_t ADCoffset=30.;    //   Float_t ADC_pC3=-5.763e-08; //  ADC/pC conversion coefficient 3
1081    Int_t ADClast=4095;      // no signal --> ADC ch=4095    
1082    Int_t ADCtof[48];    // pC < 800
1083    //Float_t ADCsat=3100;  ci pensiamo in futuro !    Float_t ADC_pC0A =   -4.437616e+01   ;
1084    //Float_t pCsat=2500;      Float_t ADC_pC1A =   1.573329e+00    ;
1085    for(Int_t i=0; i<48; i++){    Float_t ADC_pC2A =   2.780518e-04  ;
1086      QevePmt_pC[i] = 0;    Float_t ADC_pC3A =  -2.302160e-07 ;
1087      ADCtof[i]=0;    
1088    }    // pC   > 800:
1089        Float_t ADC_pC0B =    -2.245756e+02  ;
1090    // ------ read calibration file (get A1, A2, lambda1, lambda2)    Float_t ADC_pC1B =     2.184156e+00  ;
1091    ifstream fileTriggerCalib;    Float_t ADC_pC2B =     -4.171825e-04  ;
1092    TString ftrigname="TrigCalibParam.txt";    Float_t ADC_pC3B =     3.789715e-08  ;
1093    fileTriggerCalib.open(ftrigname.Data());  
1094    if ( !fileTriggerCalib ) {    Float_t pCthres=40.;     // threshold in charge
1095      printf("debug: no trigger calib file!\n");    Int_t ADClast=4095;      // no signal --> ADC ch=4095
1096      return(-117); //check output!    Int_t ADCsat=3100;       // saturation value for the ADCs
1097    };    Int_t ADCtof[48];
1098    Float_t atte1[48],atte2[48],lambda1[48],lambda2[48];  
1099    Int_t temp=0;  
1100    // correct readout WM Oct '07    // ---- introduce scale factors to tune simul ADC to real data   24-oct DC
1101    for(Int_t i=0; i<48; i++){    //   Float_t ScaleFact[48]={0.18,0.22,0.35,0.26,0.47,0.35,0.31,0.37,
1102      fileTriggerCalib >> temp;    //                     0.44,0.23,0.38,0.60,0.39,0.29,0.40,0.23,
1103      fileTriggerCalib >> atte1[i];    //                     0.30,0.66,0.22,1.53,0.17,0.55,
1104      fileTriggerCalib >> lambda1[i];    //                     0.84,0.19,0.21,1.64,0.62,0.13,
1105      fileTriggerCalib >> atte2[i];    //                     0.18,0.15,0.10,0.14,0.14,0.14,0.14,0.12,
1106      fileTriggerCalib >> lambda2[i];    //                     0.26,0.18,0.25,0.23,0.20,0.40,0.19,0.23,0.25,0.23,0.25,0.20};
1107      fileTriggerCalib >> temp;    
1108    }    // new scale factors: WM 30-Oct-07
1109    fileTriggerCalib.close();    //   Float_t ScaleFact[48]={0.35,0.41,0.32,0.34,0.58,0.47,0.42,0.44,
1110      //                     0.50,0.34,0.50,0.50,0.51,0.42,0.46,0.25,
1111    //  Read from file the 48*4 values of the attenuation fit function    //                     0.20,0.38,0.29,0.49,0.24,0.68,
1112    //  NB: lambda<0; x,y defined in gpamela (=0 in the centre of the cavity)    //                     0.30,0.26,0.28,0.79,0.31,0.12,
1113    //    Qhitpmt_pC =  atte1 * exp(x/lambda1) + atte2 * exp(x/lambda2)    //                     0.25,0.21,0.14,0.20,
1114      //                     0.16,0.17,0.19,0.18,
1115    //    fine lettura dal file */    //                     0.34,0.27,0.34,0.31,0.25,0.57,
1116      //                     0.24,0.34,0.34,0.32,0.31,0.30};
1117    //const Int_t nmax=??; = Nthtof    
1118    Int_t ip, ipad;    Float_t ScaleFact[48]={0.39, 0.49, 0.38, 0.40, 0.65, 0.51, 0.43,
1119    //Int_t ipmt;                           0.49, 0.58, 0.38, 0.53, 0.57, 0.53, 0.45, 0.49, 0.16,
1120    Int_t pmtleft=0, pmtright=0;                           0.15, 0.44, 0.28, 0.57, 0.26, 0.72, 0.37, 0.29, 0.30, 0.89,
1121    Int_t *pl, *pr;                           0.37, 0.08,  0.27, 0.23, 0.12, 0.22, 0.15, 0.16, 0.21,
1122    pl = &pmtleft;                           0.19, 0.41, 0.32, 0.39, 0.38, 0.28, 0.66, 0.28, 0.40, 0.39, 0.40, 0.37, 0.35 };
1123    pr = &pmtright;  
1124      for(Int_t i=0; i<48; i++){
1125    // TDC variables:      QevePmt_pC[i] = 0;
1126    Int_t TDClast=4095;      // no signal --> ADC ch=4095      ADCtof[i]=0;
1127    Int_t TDCint[48];    }
1128    Float_t  tdc[48],tdc1[48],tdcpmt[48];    
1129    for(Int_t i=0; i<48; i++)    // ------ read calibration file (get A1, A2, lambda1, lambda2)
1130      tdcpmt[i] = 1000.;    ifstream fileTriggerCalib;
1131    Float_t thresh=10.; // to be defined better... (Wolfgang)    TString ftrigname="TrigCalibParam.txt";
1132      fileTriggerCalib.open(ftrigname.Data());
1133      // === TDC: simulate timing for each paddle    if ( !fileTriggerCalib ) {
1134      Float_t dt1 = 285.e-12 ;   // single PMT resolution      printf("debug: no trigger calib file!\n");
1135      Float_t tdcres[50],c1_S[50],c2_S[50],c3_S[50];      return(-117); //check output!
1136      for(Int_t j=0;j<48;j++)  tdcres[j] = 50.E-12;   // TDC resolution 50 picosec    };
1137      for(Int_t j=0;j<48;j++)  c1_S[j] = 500.;  // cable length in channels    Float_t atte1[48],atte2[48],lambda1[48],lambda2[48];
1138      for(Int_t j=0;j<48;j++)  c2_S[j] = 0.;    Int_t temp=0;
1139      for(Int_t j=0;j<48;j++)  c3_S[j] = 1000.;    // correct readout WM Oct '07
1140      for(Int_t j=0;j<48;j++)  c1_S[j] = c1_S[j]*tdcres[j];   // cable length in sec    for(Int_t i=0; i<48; i++){
1141      for(Int_t j=0;j<48;j++)  c2_S[j] = c2_S[j]*tdcres[j];      fileTriggerCalib >> temp;
1142       // ih = 0 + i1;  // not used?? (Silvio)      fileTriggerCalib >> atte1[i];
1143        fileTriggerCalib >> lambda1[i];
1144    /* **********************************  start loop over hits */      fileTriggerCalib >> atte2[i];
1145          fileTriggerCalib >> lambda2[i];
1146    for(Int_t nh=0; nh<Nthtof; nh++){      fileTriggerCalib >> temp;
1147          }
1148      for(Int_t j=0; j<2; j++) { // already done!! remove???    fileTriggerCalib.close();
1149        xpath[j]=0.;  
1150        ypath[j]=0.;    Int_t ip, ipad;
1151        FGeo[j]=0.;    //Int_t ipmt;
1152      }    Int_t pmtleft=0, pmtright=0;
1153      Int_t *pl, *pr;
1154      Float_t s_l_g[6] = {8.0, 8.0, 20.9, 22.0, 9.8, 8.3 };  // length of the lightguide    pl = &pmtleft;
1155      Float_t t1,t2,veff,veff1,veff0 ;    pr = &pmtright;
1156      veff0 = 100.*1.0e8 ; // light velocity in the scintillator in m/sec  
1157      veff1 = 100.*1.5e8; // light velocity in the lightguide in m/sec    // TDC variables:
1158      veff=veff0;         // signal velocity in the paddle    Int_t TDClast=4095;      // no signal --> TDC ch=4095
1159      Int_t TDCint[48];
1160      t1 = Timetof[nh] ;  // Start    Float_t  tdc[48],tdc1[48],tdcpmt[48];
1161      t2 = Timetof[nh] ;    for(Int_t i=0; i<48; i++) {
1162        tdcpmt[i] = 1000.;
1163      // Donatella: redefinition plane and pad for vectors in C      tdc[i]  = 0.;            // 18-oct WM
1164      ip = Ipltof[nh]-1;      tdc1[i] = 0.;            // 18-oct WM
1165      ipad = Ipaddle[nh]-1;    }
1166      pmtleft=0;  
1167      pmtright=0;    Float_t thresh=10.; // to be defined better... (Wolfgang)
1168      
1169      if (ip<6) {    // === TDC: simulate timing for each paddle
1170        Paddle2Pmt(ip, ipad, &pmtleft, &pmtright);    //Float_t dt1 = 285.e-12 ;   // single PMT resolution
1171          Float_t dt1 = 425.e-12 ;   // single PMT resolution (WM, Nov'07)
1172        // per avere anche la corrispondenza pmt --> half board e canale    Float_t tdcres[50],c1_S[50],c2_S[50],c3_S[50];
1173        // metodo GetPMTIndex(Int_t ipmt, Int_t &hb, Int_t &ch) // non lo usiamo x ora    for(Int_t j=0;j<48;j++)  tdcres[j] = 50.E-12;   // TDC resolution 50 picosec
1174        for(Int_t j=0;j<48;j++)  c1_S[j] = 500.;  // cable length in channels
1175        // evaluates mean position and path inside the paddle    for(Int_t j=0;j<48;j++)  c2_S[j] = 0.;
1176        for(Int_t j=0;j<48;j++)  c3_S[j] = 1000.;
1177        Float_t tpos=0.;    for(Int_t j=0;j<48;j++)  c1_S[j] = c1_S[j]*tdcres[j];   // cable length in sec
1178        Float_t path[2] = {0., 0.};    for(Int_t j=0;j<48;j++)  c2_S[j] = c2_S[j]*tdcres[j];
1179        //--- Strip in Y = S11,S22,S31 ------    // ih = 0 + i1;  // not used?? (Silvio)
1180        if(ip==0 || ip==3 || ip==4)  
1181          tpos = (Yintof[nh]+Youttof[nh])/2.;    /* **********************************  start loop over hits */
1182        else    
1183          if(ip==1 || ip==2 || ip==5)   //--- Strip in X per S12,S21,S32    for(Int_t nh=0; nh<Nthtof; nh++){
1184            tpos = (Xintof[nh]+Xouttof[nh])/2.;      
1185          else //if (ip!=6)      Float_t s_l_g[6] = {8.0, 8.0, 20.9, 22.0, 9.8, 8.3 };  // length of the lightguide
1186            printf("*** WARNING TOF: this option should never occur! (ip=%2i, nh=%2i)\n",ip,nh);      Float_t t1,t2,veff,veff1,veff0 ;
1187        path[0]= tpos + dimel[ip]/2.;      veff0 = 100.*1.0e8 ; // light velocity in the scintillator in m/sec
1188        path[1]= dimel[ip]/2.- tpos;      veff1 = 100.*1.5e8; // light velocity in the lightguide in m/sec
1189        veff=veff0;         // signal velocity in the paddle
1190        //  cout <<"Strip N. ="<< ipaddle <<" piano n.= "<< iplane <<" POSIZ = "<< tpos <<"\n";  
1191        t1 = Timetof[nh] ;  // Start
1192        if (DEBUG) {      t2 = Timetof[nh] ;
1193          cout <<" plane "<<ip<<" strip # ="<< ipad <<" tpos  "<< tpos <<"\n";  
1194          cout <<"pmtleft, pmtright "<<pmtleft<<" "<<pmtright<<endl;      // Donatella: redefinition plane and pad for vectors in C
1195        }      ip = Ipltof[nh]-1;
1196        ipad = Ipaddle[nh]-1;
1197        // constant geometric factor, for the moment      pmtleft=0;
1198        FGeo[0] =0.5;      pmtright=0;
1199        FGeo[1] =0.5;  
1200        //  FGeo[1] = atan(path[1]/dimes[ip])/6.28318; // frazione fotoni verso SX      // WM: S12 paddles are "reversed" (Nov'07)
1201        //  FGeo[2] = atan(path[2]/dimes[ip])/6.28318; // e verso DX      if (ip==2)
1202                if (ipad==0)
1203        /*  rimando la fluttuazione poissoniana sui fotoni prodotti          ipad=1;
1204            sto studiando come funziona la funzione:        else
1205            long int i = sto.Poisson(double x);  */          ipad=0;
1206        //  Npho = Poisson(ERELTOF[nh])*Pho_keV*1e6   Eloss in GeV ?  
1207        Npho = Ereltof[nh]*Pho_keV*1.0e6;  // Eloss in GeV ?     if (ip<6) {
1208            Paddle2Pmt(ip, ipad, &pmtleft, &pmtright);
1209        Float_t knorm[2]={0., 0.}; // Donatella  
1210        Float_t Atten[2]={0., 0.}; // Donatella        // DC: evaluates mean position and path inside the paddle
1211        for(Int_t j=0; j<2; j++){    
1212          QhitPad_pC[j]= Npho*FGeo[j]*effi*pmGain*echarge*1.E12; // corrected WM        Float_t tpos=0.;
1213          /*      knorm[j]=QhitPad_pC[j]/(atte1[pmtleft+j]*exp((dimel[ip]/2.*pow(-1,j+1))/lambda1[pmtleft+j]) +        Float_t path[2] = {0., 0.};
1214                                  atte2[pmtleft+j]*exp((dimel[ip]/2.*pow(-1,j+1))/lambda2[pmtleft+j]));        //--- Strip in Y = S11,S22,S31 ------
1215          Atten[j]=knorm[j]*(atte1[pmtleft+j]*exp(tpos/lambda1[pmtleft+j]) +        if(ip==0 || ip==3 || ip==4)
1216                             atte2[pmtleft+j]*exp(tpos/lambda2[pmtleft+j]));          tpos = (Yintof[nh]+Youttof[nh])/2.;
1217          QhitPmt_pC[j]= QhitPad_pC[j]*Atten[j];        else
1218          */          if(ip==1 || ip==2 || ip==5)   //--- Strip in X for S12,S21,S32
1219          // WM            tpos = (Xintof[nh]+Xouttof[nh])/2.;
1220          knorm[j]=atte1[pmtleft+j]*exp(lambda1[pmtleft+j]*dimel[ip]/2.*pow(-1,j+1)) +          else //if (ip!=6)
1221            atte2[pmtleft+j]*exp(lambda2[pmtleft+j]*dimel[ip]/2.*pow(-1,j+1));            printf("*** WARNING TOF: this option should never occur! (ip=%2i, nh=%2i)\n",ip,nh);
1222          Atten[j]=atte1[pmtleft+j]*exp(tpos*lambda1[pmtleft+j]) +  
1223            atte2[pmtleft+j]*exp(tpos*lambda2[pmtleft+j]) ;        path[0]= tpos + dimel[ip]/2.;   // path to left PMT
1224          QhitPmt_pC[j]= QhitPad_pC[j]*Atten[j]/knorm[j];        path[1]= dimel[ip]/2.- tpos;    // path to right PMT
1225          if (DEBUG) {  
1226            cout<<"pmtleft "<<pmtleft<<" j "<<j<<endl;        //  cout <<"Strip N. ="<< ipaddle <<" piano n.= "<< iplane <<" POSIZ = "<< tpos <<"\n";
1227            cout<<" atte1 "<<atte1[pmtleft+j]<<"lambda1 "<<lambda1[pmtleft+j]<<" atte2 "<<atte2[pmtleft+j]<<"lambda2 "<<lambda2[pmtleft+j] <<endl;            
1228            cout<<j<<" tpos "<<tpos<<" knorm "<<knorm[j]<<" "<<Atten[j]<<" "<<"QhitPmt_pC "<<QhitPmt_pC[j]<<endl;            if (DEBUG) {
1229          }          cout <<" plane "<<ip<<" strip # ="<< ipad <<" tpos  "<< tpos <<"\n";
1230        }          cout <<"pmtleft, pmtright "<<pmtleft<<" "<<pmtright<<endl;
1231                }
1232        if (DEBUG)        
1233          cout<<"Npho "<<Npho<<" QhitPmt_pC "<<QhitPmt_pC[0]<<" "<<QhitPmt_pC[1]<<endl;          // constant geometric factor, the rest is handled by the scaling factor
1234          FGeo[0] =0.5;
1235        QevePmt_pC[pmtleft]  += QhitPmt_pC[0];        FGeo[1] =0.5;
1236        QevePmt_pC[pmtright] += QhitPmt_pC[1];        //  FGeo[1] = atan(path[1]/dimes[ip])/6.28318; // fraction of photons toward left
1237                //  FGeo[2] = atan(path[2]/dimes[ip])/6.28318; // toward right
1238        // TDC        
1239        t2 = t2 + fabs(path[0]/veff) + s_l_g[ip]/veff1 ;  // Signal reaches PMT        
1240        t1 = t1 + fabs(path[1]/veff) + s_l_g[ip]/veff1;        //  Npho = Poisson(ERELTOF[nh])*Pho_keV*1e6  Poissonian fluctuations to be inserted-DC
1241                Npho = Ereltof[nh]*Pho_keV*1.0e6;  // Eloss in GeV
1242        TRandom r;        
1243        t1 = r.Gaus(t1,dt1);  //apply gaussian error  dt        Float_t knorm[2]={0., 0.}; // Donatella
1244        t2 = r.Gaus(t2,dt1);  //apply gaussian error  dt        Float_t Atten[2]={0., 0.}; // Donatella
1245                for(Int_t j=0; j<2; j++){
1246        t1 = t1 + c1_S[pmtleft] ;  // Signal reaches Discriminator ,TDC starts  to run          QhitPad_pC[j]= Npho*FGeo[j]*effi*pmGain*echarge*1.E12*ScaleFact[pmtleft+j];
1247        t2 = t2 + c1_S[pmtright] ;          // WM
1248                  knorm[j]=atte1[pmtleft+j]*exp(lambda1[pmtleft+j]*dimel[ip]/2.*pow(-1,j+1)) +
1249        // check if signal is above threshold            atte2[pmtleft+j]*exp(lambda2[pmtleft+j]*dimel[ip]/2.*pow(-1,j+1));
1250        // then check if tdcpmt is already filled by another hit...          Atten[j]=atte1[pmtleft+j]*exp(tpos*lambda1[pmtleft+j]) +
1251        // only re-fill if time is smaller            atte2[pmtleft+j]*exp(tpos*lambda2[pmtleft+j]) ;
1252                  QhitPmt_pC[j]= QhitPad_pC[j]*Atten[j]/knorm[j];
1253        if (QhitPmt_pC[0] > thresh) {          //              QhitPmt_pC[j]= QhitPad_pC[j]; //no attenuation
1254          if (tdcpmt[pmtleft] == 1000.) {  // fill for the first time  
1255            tdcpmt[pmtleft] = t1;  
1256            tdc[pmtleft] = t1 + c2_S[pmtleft] ;  // Signal reaches Coincidence          if (DEBUG) {
1257          }            cout<<"pmtleft "<<pmtleft<<" j "<<j<<endl;
1258          if (tdcpmt[pmtleft] < 1000.) // is already filled!            cout<<" atte1 "<<atte1[pmtleft+j]<<"lambda1 "<<lambda1[pmtleft+j]<<" atte2 "<<atte2[pmtleft+j]<<"lambda2 "<<lambda2[pmtleft+j] <<endl;    
1259            if (t1 <  tdcpmt[pmtleft]) {            cout<<j<<" tpos "<<tpos<<" knorm "<<knorm[j]<<" "<<Atten[j]<<" "<<"QhitPmt_pC "<<QhitPmt_pC[j]<<endl;    
1260              tdcpmt[pmtleft] = t1;          }
1261              t1 = t1 + c2_S[pmtleft] ;  // Signal reaches Coincidence        }
1262              tdc[pmtleft] = t1;        
1263            }        if (DEBUG)
1264        }                cout<<"Npho "<<Npho<<" QhitPmt_pC "<<QhitPmt_pC[0]<<" "<<QhitPmt_pC[1]<<endl;  
1265        if (QhitPmt_pC[1] > thresh) {        
1266          if (tdcpmt[pmtright] == 1000.) {  // fill for the first time        QevePmt_pC[pmtleft]  += QhitPmt_pC[0];
1267            tdcpmt[pmtright] = t2;        QevePmt_pC[pmtright] += QhitPmt_pC[1];
1268            tdc[pmtright] = t2 + c2_S[pmtright] ;  // Signal reaches Coincidence        
1269          }        // TDC
1270          if (tdcpmt[pmtright] < 1000.)  // is already filled!        // WM right and left <->
1271            if (t2 <  tdcpmt[pmtright]) {        //      t2 = t2 + fabs(path[0]/veff) + s_l_g[ip]/veff1 ;  // Signal reaches PMT
1272              tdcpmt[pmtright] = t2;        //      t1 = t1 + fabs(path[1]/veff) + s_l_g[ip]/veff1;
1273              t2 = t2 + c2_S[pmtright] ;  
1274              tdc[pmtright] = t2;        t1 = t1 + fabs(path[0]/veff) + s_l_g[ip]/veff1;
1275            }              t2 = t2 + fabs(path[1]/veff) + s_l_g[ip]/veff1 ;  // Signal reaches PMT
1276        }        
1277          t1 = gRandom->Gaus(t1,dt1); //apply gaussian error  dt
1278        if (DEBUG)        t2 = gRandom->Gaus(t2,dt1); //apply gaussian error  dt
1279          cout<<nh<<" "<<Timetof[nh]<<" "<<t1<<" "<<t2<<endl;  
1280          t1 = t1 + c1_S[pmtleft] ;  // Signal reaches Discriminator ,TDC starts  to run
1281      } // ip < 6        t2 = t2 + c1_S[pmtright] ;
1282          
1283    }; // ****************************************       end loop over hits        // check if signal is above threshold
1284            // then check if tdcpmt is already filled by another hit...
1285    // ======  ADC ======        // only re-fill if time is smaller
1286    for(Int_t i=0; i<48; i++){        
1287      if(QevePmt_pC[i] != 0.){        if (QhitPmt_pC[0] > thresh) {
1288        ADCtof[i]= (Int_t)(ADC_pC*QevePmt_pC[i] + ADCoffset);          if (tdcpmt[pmtleft] == 1000.) {  // fill for the first time
1289        if(ADCtof[i]> ADClast) ADCtof[i]=ADClast;            tdcpmt[pmtleft] = t1;
1290      } else            tdc[pmtleft] = t1 + c2_S[pmtleft] ;  // Signal reaches Coincidence
1291        ADCtof[i]= ADClast;          }
1292    }          if (tdcpmt[pmtleft] < 1000.) // is already filled!
1293              if (t1 <  tdcpmt[pmtleft]) {
1294                    tdcpmt[pmtleft] = t1;
1295    // ======  build  TDC coincidence  ======              t1 = t1 + c2_S[pmtleft] ;  // Signal reaches Coincidence
1296                tdc[pmtleft] = t1;
1297    Float_t t_coinc = 0;            }
1298    Int_t ilast = 100;        }      
1299    for (Int_t ii=0; ii<48;ii++)        if (QhitPmt_pC[1] > thresh) {
1300      if (tdc[ii] > t_coinc) {          if (tdcpmt[pmtright] == 1000.) {  // fill for the first time
1301        t_coinc = tdc[ii];            tdcpmt[pmtright] = t2;
1302        ilast = ii;            tdc[pmtright] = t2 + c2_S[pmtright] ;  // Signal reaches Coincidence
1303      }          }
1304              if (tdcpmt[pmtright] < 1000.)  // is already filled!
1305    //     cout<<ilast<<" "<<t_coinc<<endl;            if (t2 <  tdcpmt[pmtright]) {
1306    //     At t_coinc  trigger condition is fulfilled              tdcpmt[pmtright] = t2;
1307                  t2 = t2 + c2_S[pmtright] ;
1308    for (Int_t ii=0; ii<48;ii++){              tdc[pmtright] = t2;
1309      //      if (tdc[ii] != 0) tdc1[ii] = t_coinc - tdc[ii];   // test 1            }      
1310      if (tdc[ii] != 0) tdc1[ii] = t_coinc - tdcpmt[ii];  // test 2        }
1311      tdc1[ii] = tdc1[ii]/tdcres[ii];                     // divide by TDC resolution  
1312      if (tdc[ii] != 0) tdc1[ii] = tdc1[ii] + c3_S[ii];  // add cable length c3        if (DEBUG)
1313            cout<<nh<<" "<<Timetof[nh]<<" "<<t1<<" "<<t2<<endl;
1314    } // missing parenthesis inserted! (Silvio)  
1315        } // ip < 6
1316    for(Int_t i=0; i<48; i++){  
1317      if(tdc1[i] != 0.){    }; // ****************************************       end loop over hits
1318        TDCint[i]=(Int_t)tdc1[i];    
1319        if (DEBUG)    // ======  ADC ======
1320          cout<<i<<" "<<TDCint[i]<<endl;  
1321        //ADC[i]= ADC_pC * QevePmt_pC[i] + ADCoffset;    for(Int_t i=0; i<48; i++){
1322        //if(ADC[i]> ADClast) ADC[i]=ADClast;      if (QevePmt_pC[i] < 800.)  ADCtof[i]= (Int_t)(ADC_pC0A + ADC_pC1A*QevePmt_pC[i] + ADC_pC2A*pow(QevePmt_pC[i],2) + ADC_pC3A*pow(QevePmt_pC[i],3));
1323      } else      if (QevePmt_pC[i] > 800.)  ADCtof[i]= (Int_t)(ADC_pC0B + ADC_pC1B*QevePmt_pC[i] + ADC_pC2B*pow(QevePmt_pC[i],2) + ADC_pC3B*pow(QevePmt_pC[i],3));
1324        TDCint[i]= TDClast;      if (QevePmt_pC[i] > 2485.) ADCtof[i]= (Int_t)(1758. + 0.54*QevePmt_pC[i]);  //assuming a fictional 0.54 ch/pC above ADCsat
1325    }      if (ADCtof[i]>ADCsat) ADCtof[i]=ADCsat;
1326        if (QevePmt_pC[i] < pCthres)  ADCtof[i]= ADClast;
1327    if (DEBUG)      if (ADCtof[i] < 0) ADCtof[i]=ADClast;    
1328      cout<<"-----------"<<endl;      if (ADCtof[i] > ADClast) ADCtof[i]=ADClast;
1329      }
1330  // ======  write fDataTof  =======  
1331    UChar_t tofBin;  //   for(Int_t i=0; i<48; i++){
1332    for (Int_t j=0; j < 12; j++){  //     if(QevePmt_pC[i] >= pCthres){
1333      Int_t j12=j*12;  //       ADCtof[i]= (Int_t)(ADC_pC0 + ADC_pC1*QevePmt_pC[i] + ADC_pC2*pow(QevePmt_pC[i],2) + ADC_pC3*pow(QevePmt_pC[i],3));
1334      fDataTof[j12+0]=0x00;   // TDC_ID  //   } else
1335      fDataTof[j12+1]=0x00;   // EV_COUNT  //       ADCtof[i]= ADClast;  
1336      fDataTof[j12+2]=0x00;   // TDC_MASK (1)  // }
1337      fDataTof[j12+3]=0x00;   // TDC_MASK (2)    
1338      for (Int_t k=0; k < 4; k++){  // // ---- introduce scale factors to tune simul ADC to real data   24-oct DC
1339        Int_t jk12=j12+k;  
1340        tofBin=(UChar_t)(ADCtof[k+4*j]/256);   // ADC# (msb) (#=1+k+4*j)  //   for(Int_t i=0; i<48; i++){
1341        fDataTof[jk12+4] = Bin2GrayTof(tofBin,fDataTof[jk12+4]);  //     if(ADCtof[i] != ADClast){
1342        tofBin=(UChar_t)(ADCtof[k+4*j]%256);   // ADC# (lsb)  //                              //      printf("%3d, %4d, %4.2f\n",i, ADCtof[i],ScaleFact[i]);
1343        fDataTof[jk12+5] = Bin2GrayTof(tofBin,fDataTof[jk12+5]);  //       ADCtof[i]= Int_t (ADCtof[i]*ScaleFact[i]);
1344        tofBin=(UChar_t)(TDCint[k+4*j]/256);   // TDC# (msb)  //                              //      printf("%3d, %4d,\n",i, ADCtof[i]);
1345        fDataTof[jk12+6]=Bin2GrayTof(tofBin,fDataTof[jk12+6]);  //     }
1346        tofBin=(UChar_t)(TDCint[k+4*j]%256);   // TDC# (lsb)  //   }
1347        fDataTof[jk12+7]=Bin2GrayTof(tofBin,fDataTof[jk12+7]);  
1348      };  //   for(Int_t i=0; i<48; i++){
1349      fDataTof[j12+20]=0x00;   // TEMP1  //     if(ADCtof[i] != ADClast){
1350      fDataTof[j12+21]=0x00;   // TEMP2  //       if(ADCtof[i]> ADCsat) ADCtof[i]=ADCsat;
1351      fDataTof[j12+22]= EvaluateCrcTof(pTof);   // CRC  //       else if(ADCtof[i]< 0) ADCtof[i]=ADClast;    
1352      pTof+=23;  //   }
1353    };  //   }    
1354    return(0);  
1355  };  
1356    // ======  build  TDC coincidence  ======
1357  UChar_t Digitizer::Bin2GrayTof(UChar_t binaTOF,UChar_t grayTOF){  
1358    union graytof_data {    Float_t t_coinc = 0;
1359      UChar_t word;    Int_t ilast = 100;
1360      struct bit_field {    for (Int_t ii=0; ii<48;ii++)
1361        unsigned b0:1;      if (tdc[ii] > t_coinc) {
1362        unsigned b1:1;        t_coinc = tdc[ii];
1363        unsigned b2:1;        ilast = ii;
1364        unsigned b3:1;      }
1365        unsigned b4:1;    
1366        unsigned b5:1;    //     cout<<ilast<<" "<<t_coinc<<endl;
1367        unsigned b6:1;    //     At t_coinc  trigger condition is fulfilled
1368        unsigned b7:1;    
1369      } bit;    for (Int_t ii=0; ii<48;ii++){
1370    } bi,gr;      //      if (tdc[ii] != 0) tdc1[ii] = t_coinc - tdc[ii];   // test 1
1371    //      if (tdc[ii] != 0) tdc1[ii] = t_coinc - tdcpmt[ii];  // test 2
1372    bi.word = binaTOF;      tdc1[ii] = tdc1[ii]/tdcres[ii];                     // divide by TDC resolution
1373    gr.word = grayTOF;      if (tdc[ii] != 0) tdc1[ii] = tdc1[ii] + c3_S[ii];  // add cable length c3
1374    //    } // missing parenthesis inserted! (Silvio)
1375    gr.bit.b0 = bi.bit.b1 ^ bi.bit.b0;  
1376    gr.bit.b1 = bi.bit.b2 ^ bi.bit.b1;    for(Int_t i=0; i<48; i++){
1377    gr.bit.b2 = bi.bit.b3 ^ bi.bit.b2;      if(tdc1[i] != 0.){
1378    gr.bit.b3 = bi.bit.b3;        TDCint[i]=(Int_t)tdc1[i];
1379    //        if (TDCint[i]>4093) TDCint[i]=TDClast;  // 18-oct WM
1380    /* bin to gray conversion 4 bit per time*/        if (DEBUG)
1381    //          cout<<i<<" "<<TDCint[i]<<endl;
1382    gr.bit.b4 = bi.bit.b5 ^ bi.bit.b4;        //ADC[i]= ADC_pC * QevePmt_pC[i] + ADCoffset;
1383    gr.bit.b5 = bi.bit.b6 ^ bi.bit.b5;        //if(ADC[i]> ADClast) ADC[i]=ADClast;
1384    gr.bit.b6 = bi.bit.b7 ^ bi.bit.b6;      } else
1385    gr.bit.b7 = bi.bit.b7;        TDCint[i]= TDClast;
1386    //    }
1387    return(gr.word);  
1388  }    if (DEBUG)
1389        cout<<"-----------"<<endl;
1390  UChar_t Digitizer::EvaluateCrcTof(UChar_t *pTof) {  
1391    // UChar_t crcTof=0x00;  
1392    //   for (Int_t jp=0; jp < 23; jp++){  //------ use channelmap  18-oct WM
1393    //     crcTof = crc8(...)  
1394    //   }    Int_t  channelmap[] =  {3,21,11,29,19,45,27,37,36,28,44,20,5,12,13,4,
1395    return(0x00);                          6,47,14,39,22,31,30,23,38,15,46,7,0,33,16,24,
1396  };                          8,41,32,40,25,17,34,9,42,1,2,10,18,26,35,43};
1397    
1398  //void Digitizer::Paddle2Pmt(Int_t plane, Int_t paddle, Int_t* &pmtleft, Int_t* &pmtright){    Int_t ADChelp[48];
1399  void Digitizer::Paddle2Pmt(Int_t plane, Int_t paddle, Int_t *pl, Int_t *pr){    Int_t TDChelp[48];
1400    //* @param plane    (0 - 5)  
1401    //* @param paddle   (plane=0, paddle = 0,...5)    for(Int_t i=0; i<48; i++){
1402    //* @param padid    (0 - 23)        Int_t ii=channelmap[i];
1403    //      ADChelp[ii]= ADCtof[i];
1404    Int_t padid=-1;      TDChelp[ii]= TDCint[i];
1405    Int_t pads[6]={8,6,2,2,3,3};    }
1406    //  
1407    Int_t somma=0;    for(Int_t i=0; i<48; i++){
1408    Int_t np=plane;      ADCtof[i]= ADChelp[i];
1409    for(Int_t j=0; j<np; j++)      TDCint[i]= TDChelp[i];
1410      somma+=pads[j];    }
1411    padid=paddle+somma;  
1412    *pl = padid*2;  
1413    //  *pr = *pr + 1;  // ======  write fDataTof  =======
1414    *pr = *pl + 1; // WM  
1415  };  
1416    //  UChar_t tdcadd[8]={1,0,3,2,5,4,7,6};  (coded in 3 bit)
1417  void Digitizer::DigitizeAC() {    UChar_t Ctrl3bit[8]={32,0,96,64,160,128,224,192};  // DC (msb in 8 bit word )
1418    // created:  J. Conrad, KTH    
1419    // modified: S. Orsi, INFN Roma2    UChar_t tofBin;
1420    // fDataAC[0-63]:   main AC board    for (Int_t j=0; j < 12; j++){   // loop on TDC #12
1421    // fDataAC[64-127]: extra AC board      Int_t j12=j*23;               // for each TDC 23 bytes (8 bits)
1422        fDataTof[j12+0]=0x00;   // TDC_ID
1423    fDataAC[0] = 0xACAC;      fDataTof[j12+1]=0x00;   // EV_COUNT
1424    fDataAC[64]= 0xACAC;      fDataTof[j12+2]=0x00;   // TDC_MASK (1)
1425    fDataAC[1] = 0xAC11;        fDataTof[j12+3]=0x00;   // TDC_MASK (2)
1426    fDataAC[65] = 0xAC22;        for (Int_t k=0; k < 4; k++){   // for each TDC 4 channels (ADC+TDC)
1427              
1428    // the third word is a status word (dummy: "no errors are present in the AC boards")        Int_t jk12=j12+4*k;         // ADC,TDC channel (0-47)
1429    fDataAC[2] = 0xFFFF; //FFEF?  
1430    fDataAC[66] = 0xFFFF;        tofBin =(UChar_t)(ADCtof[k+4*j]/256);   // ADC# (msb)
1431          fDataTof[jk12+4] = Bin2GrayTof(tofBin,fDataTof[jk12+4]);
1432    const UInt_t nReg = 6;        /* control bits inserted here, after the bin to gray conv - DC*/
1433          fDataTof[jk12+4] = Ctrl3bit[2*k] | fDataTof[jk12+4];
1434    // FPGA Registers (dummy)        tofBin=(UChar_t)(ADCtof[k+4*j]%256);   // ADC# (lsb)
1435    for (UInt_t i=0; i<=nReg; i++){        fDataTof[jk12+5] = Bin2GrayTof(tofBin,fDataTof[jk12+5]);
1436      fDataAC[i+4] = 0xFFFF;        tofBin=(UChar_t)(TDCint[k+4*j]/256);   // TDC# (msb)
1437      fDataAC[i+68] = 0xFFFF;        fDataTof[jk12+6]=Bin2GrayTof(tofBin,fDataTof[jk12+6]);
1438    }        /* control bits inserted here, after the bin to gray conv - DC*/
1439          fDataTof[jk12+6] = Ctrl3bit[2*k+1] | fDataTof[jk12+6];
1440    // the last word is a CRC        tofBin=(UChar_t)(TDCint[k+4*j]%256);   // TDC# (lsb)
1441    // Dummy for the time being, but it might need to be calculated in the end        fDataTof[jk12+7]=Bin2GrayTof(tofBin,fDataTof[jk12+7]);
1442    fDataAC[63] = 0xABCD;      };
1443    fDataAC[127] = 0xABCD;      fDataTof[j12+20]=0x00;   // TEMP1
1444        fDataTof[j12+21]=0x00;   // TEMP2
1445    // shift registers (moved to the end of the routine)      fDataTof[j12+22]= EvaluateCrcTof(pTof);   // CRC
1446        pTof+=23;
1447    Int_t evntLSB=Ievnt%65536;    };
1448    Int_t evntMSB=(Int_t)(Ievnt/65536);    return(0);
1449    };
1450    // singles counters are dummy  
1451    for (UInt_t i=0; i<=15; i++){  //SO Oct '07: // for (UInt_t i=0; i<=16; i++){  
1452      //     fDataAC[i+26] = 0x0000;    UChar_t Digitizer::Bin2GrayTof(UChar_t binaTOF,UChar_t grayTOF){
1453      //     fDataAC[i+90] = 0x0000;    union graytof_data {
1454      fDataAC[i+26] = evntLSB;      UChar_t word;
1455      fDataAC[i+90] = evntLSB;      struct bit_field {
1456    };        unsigned b0:1;
1457            unsigned b1:1;
1458    // coincidences are dummy (increment by 1 at each event)        unsigned b2:1;
1459    // for (UInt_t i=0; i<=7; i++){        unsigned b3:1;
1460    //    fDataAC[i+42] = 0x0000;        unsigned b4:1;
1461    //    fDataAC[i+106] = 0x0000;        unsigned b5:1;
1462    //   }        unsigned b6:1;
1463    for (UInt_t i=0; i<=7; i++){        unsigned b7:1;
1464      fDataAC[i+42] = evntLSB;      } bit;
1465      fDataAC[i+106] = evntLSB;    } bi,gr;
1466    };    //
1467      bi.word = binaTOF;
1468    // increments for every trigger might be needed at some point.    gr.word = grayTOF;
1469    // dummy for now    //
1470    fDataAC[50]  = 0x0000;    gr.bit.b0 = bi.bit.b1 ^ bi.bit.b0;
1471    fDataAC[114] = 0x0000;    gr.bit.b1 = bi.bit.b2 ^ bi.bit.b1;
1472      gr.bit.b2 = bi.bit.b3 ^ bi.bit.b2;
1473    // dummy FPGA clock (increment by 1 at each event)    gr.bit.b3 = bi.bit.b3;
1474    /*        //
1475      fDataAC[51] = 0x006C;    /* bin to gray conversion 4 bit per time*/
1476      fDataAC[52] = 0x6C6C;    //
1477      fDataAC[115] = 0x006C;    gr.bit.b4 = bi.bit.b5 ^ bi.bit.b4;
1478      fDataAC[116] = 0x6C6C;    gr.bit.b5 = bi.bit.b6 ^ bi.bit.b5;
1479    */    gr.bit.b6 = bi.bit.b7 ^ bi.bit.b6;
1480    if (Ievnt<=0xFFFF) {    gr.bit.b7 = bi.bit.b7;
1481      fDataAC[51] = 0x0000;    //
1482      fDataAC[52] = Ievnt;    return(gr.word);
1483      fDataAC[115] = 0x0000;  }
1484      fDataAC[116] = Ievnt;  
1485    } else {  UChar_t Digitizer::EvaluateCrcTof(UChar_t *pTof) {
1486      fDataAC[51] = evntMSB;    Bool_t DEBUG=false;
1487      fDataAC[52] = evntLSB;    if (DEBUG)
1488      fDataAC[115] = fDataAC[51];      return(0x00);
1489      fDataAC[116] = fDataAC[52];  
1490    }    UChar_t crcTof=0x00;
1491      UChar_t *pc=&crcTof, *pc2;
1492    // dummy temperatures    pc2=pTof;
1493    fDataAC[53] = 0x0000;    for (Int_t jp=0; jp < 23; jp++){
1494    fDataAC[54] = 0x0000;      //crcTof = crc8(...)
1495    fDataAC[117] = 0x0000;      Crc8Tof(pc2++,pc);
1496    fDataAC[118] = 0x0000;      //    printf("%2i --- %x\n",jp,crcTof);
1497      }
1498      return(crcTof);
1499    // dummy DAC thresholds  }
1500    for (UInt_t i=0; i<=7; i++){  
1501      fDataAC[i+55] = 0x1A13;    void Digitizer::Crc8Tof(UChar_t *oldCRC, UChar_t *crcTof){
1502      fDataAC[i+119] = 0x1A13;    union crctof_data {
1503    }      UChar_t word;
1504          struct bit_field {
1505    // We activate all branches. Once the digitization algorithm is determined        unsigned b0:1;
1506    // only the branches that involve needed information will be activated        unsigned b1:1;
1507            unsigned b2:1;
1508    fhBookTree->SetBranchAddress("Ievnt",&Ievnt);        unsigned b3:1;
1509    fhBookTree->SetBranchStatus("Nthcat",1);        unsigned b4:1;
1510    fhBookTree->SetBranchStatus("Iparcat",1);        unsigned b5:1;
1511    fhBookTree->SetBranchStatus("Icat",1);        unsigned b6:1;
1512    fhBookTree->SetBranchStatus("Xincat",1);        unsigned b7:1;
1513    fhBookTree->SetBranchStatus("Yincat",1);      } bit;
1514    fhBookTree->SetBranchStatus("Zincat",1);    } c,d,r;
1515    fhBookTree->SetBranchStatus("Xoutcat",1);  
1516    fhBookTree->SetBranchStatus("Youtcat",1);    c.word = *oldCRC;
1517    fhBookTree->SetBranchStatus("Zoutcat",1);    //d.word = *newCRC;
1518    fhBookTree->SetBranchStatus("Erelcat",1);    d.word = *crcTof;
1519    fhBookTree->SetBranchStatus("Timecat",1);    r.word = 0;
1520    fhBookTree->SetBranchStatus("Pathcat",1);  
1521    fhBookTree->SetBranchStatus("P0cat",1);    r.bit.b0 = c.bit.b7 ^ c.bit.b6 ^ c.bit.b0 ^
1522    fhBookTree->SetBranchStatus("Nthcas",1);               d.bit.b0 ^ d.bit.b6 ^ d.bit.b7;
1523    fhBookTree->SetBranchStatus("Iparcas",1);  
1524    fhBookTree->SetBranchStatus("Icas",1);    r.bit.b1 = c.bit.b6 ^ c.bit.b1 ^ c.bit.b0 ^
1525    fhBookTree->SetBranchStatus("Xincas",1);               d.bit.b0 ^ d.bit.b1 ^ d.bit.b6;
1526    fhBookTree->SetBranchStatus("Yincas",1);  
1527    fhBookTree->SetBranchStatus("Zincas",1);    r.bit.b2 = c.bit.b6 ^ c.bit.b2 ^ c.bit.b1 ^ c.bit.b0 ^
1528    fhBookTree->SetBranchStatus("Xoutcas",1);               d.bit.b0 ^ d.bit.b1 ^ d.bit.b2 ^ d.bit.b6;
1529    fhBookTree->SetBranchStatus("Youtcas",1);  
1530    fhBookTree->SetBranchStatus("Zoutcas",1);    r.bit.b3 = c.bit.b7 ^ c.bit.b3 ^ c.bit.b2 ^ c.bit.b1 ^
1531    fhBookTree->SetBranchStatus("Erelcas",1);               d.bit.b1 ^ d.bit.b2 ^ d.bit.b3 ^ d.bit.b7;
1532    fhBookTree->SetBranchStatus("Timecas",1);  
1533    fhBookTree->SetBranchStatus("Pathcas",1);    r.bit.b4 = c.bit.b4 ^ c.bit.b3 ^ c.bit.b2 ^
1534    fhBookTree->SetBranchStatus("P0cas",1);               d.bit.b2 ^ d.bit.b3 ^ d.bit.b4;
1535    fhBookTree->SetBranchStatus("Nthcard",1);  
1536    fhBookTree->SetBranchStatus("Iparcard",1);    r.bit.b5 = c.bit.b5 ^ c.bit.b4 ^ c.bit.b3 ^
1537    fhBookTree->SetBranchStatus("Icard",1);               d.bit.b3 ^ d.bit.b4 ^ d.bit.b5;
1538    fhBookTree->SetBranchStatus("Xincard",1);  
1539    fhBookTree->SetBranchStatus("Yincard",1);    r.bit.b6 = c.bit.b6 ^ c.bit.b5 ^ c.bit.b4 ^
1540    fhBookTree->SetBranchStatus("Zincard",1);               d.bit.b4 ^ d.bit.b5 ^ d.bit.b6;
1541    fhBookTree->SetBranchStatus("Xoutcard",1);  
1542    fhBookTree->SetBranchStatus("Youtcard",1);    r.bit.b7 = c.bit.b7 ^ c.bit.b6 ^ c.bit.b5 ^
1543    fhBookTree->SetBranchStatus("Zoutcard",1);               d.bit.b5 ^ d.bit.b6 ^ d.bit.b7 ;
1544    fhBookTree->SetBranchStatus("Erelcard",1);  
1545    fhBookTree->SetBranchStatus("Timecard",1);    *crcTof=r.word;
1546    fhBookTree->SetBranchStatus("Pathcard",1);    //return r.word;
1547    fhBookTree->SetBranchStatus("P0card",1);  };
1548    
1549    // In this simpliefied approach we will assume that once  //void Digitizer::Paddle2Pmt(Int_t plane, Int_t paddle, Int_t* &pmtleft, Int_t* &pmtright){
1550    // a particle releases > 0.5 mip in one of the 12 AC detectors it  void Digitizer::Paddle2Pmt(Int_t plane, Int_t paddle, Int_t *pl, Int_t *pr){
1551    // will fire. We will furthermore assume that both cards read out    //* @param plane    (0 - 5)
1552    // identical data.    //* @param paddle   (plane=0, paddle = 0,...5)
1553      //* @param padid    (0 - 23)  
1554    // If you develop your digitization algorithm, you should start by    //
1555    // identifying the information present in level2 (post-darth-vader)    Int_t padid=-1;
1556    // data.    Int_t pads[6]={8,6,2,2,3,3};
1557      //
1558    Float_t SumEcat[5];    Int_t somma=0;
1559    Float_t SumEcas[5];    Int_t np=plane;
1560    Float_t SumEcard[5];    for(Int_t j=0; j<np; j++)
1561    for (Int_t k= 0;k<5;k++){      somma+=pads[j];
1562      SumEcat[k]=0.;    padid=paddle+somma;
1563      SumEcas[k]=0.;    *pl = padid*2;
1564      SumEcard[k]=0.;    //  *pr = *pr + 1;
1565    };    *pr = *pl + 1; // WM
1566    };
1567    if (Nthcat>50 || Nthcas>50 || Nthcard>50)  
1568      printf("*** ERROR AC! NthAC out of range!\n\n");  void Digitizer::DigitizeAC() {
1569      // created:  J. Conrad, KTH
1570    // energy dependence on position (see file AcFitOutputDistancePmt.C by S.Orsi)    // modified: S. Orsi, INFN Roma2
1571    // based on J.Lundquist's calculations (PhD thesis, page 94)    // fDataAC[0-63]:   main AC board
1572    // function: [0]+[1]*atan([2]/(x+1)), where the 3 parameters are:    // fDataAC[64-127]: extra AC board
1573    //   8.25470e-01   +- 1.79489e-02  
1574    //   6.41609e-01   +- 2.65846e-02    fDataAC[0] = 0xACAC;
1575    //   9.81177e+00   +- 1.21284e+00    fDataAC[64]= 0xACAC;
1576    // hp: 1 minimum ionising particle at 35cm from the PMT releases 1mip    fDataAC[1] = 0xAC11;  
1577    //    fDataAC[65] = 0xAC22;  
1578    // NB: the PMT positions are needed!  
1579      // the third word is a status word (dummy: "no errors are present in the AC boards")
1580    // look in CAT    fDataAC[2] = 0xFFFF; //FFEF?
1581    //  for (UInt_t k= 0;k<50;k++){    fDataAC[66] = 0xFFFF;
1582    for (Int_t k= 0;k<Nthcat;k++){  
1583      if (Erelcat[k] > 0)    const UInt_t nReg = 6;
1584        SumEcat[Icat[k]] += Erelcat[k];  
1585    };    // FPGA Registers (dummy)
1586      for (UInt_t i=0; i<=nReg; i++){
1587    // look in CAS      fDataAC[i+4] = 0xFFFF;
1588    for (Int_t k= 0;k<Nthcas;k++){      fDataAC[i+68] = 0xFFFF;
1589      if (Erelcas[k] >0)    }
1590        SumEcas[Icas[k]] += Erelcas[k];  
1591    };    // the last word is a CRC
1592      // Dummy for the time being, but it might need to be calculated in the end
1593    // look in CARD    fDataAC[63] = 0xABCD;
1594    for (Int_t k= 0;k<Nthcard;k++){    fDataAC[127] = 0xABCD;
1595      if (Erelcard[k] >0)  
1596        SumEcard[Icard[k]] += Erelcard[k];    // shift registers (moved to the end of the routine)
1597    };  
1598      Int_t evntLSB=Ievnt%65536;
1599    // channel mapping              Hit Map    Int_t evntMSB=(Int_t)(Ievnt/65536);
1600    // 1 CARD4                      0          LSB  
1601    // 2 CAT2                       0    // singles counters are dummy
1602    // 3 CAS1                       0    for (UInt_t i=0; i<=15; i++){  //SO Oct '07: // for (UInt_t i=0; i<=16; i++){
1603    // 4 NC                         0      //     fDataAC[i+26] = 0x0000;  
1604    // 5 CARD2                      0      //     fDataAC[i+90] = 0x0000;
1605    // 6 CAT4                       1      fDataAC[i+26] = evntLSB;
1606    // 7 CAS4                       0        fDataAC[i+90] = evntLSB;
1607    // 8 NC                         0    };
1608    // 9 CARD3                      0    
1609    // 10 CAT3                      0    // coincidences are dummy (increment by 1 at each event)
1610    // 11 CAS3                      0    // for (UInt_t i=0; i<=7; i++){
1611    // 12 NC                        0    //    fDataAC[i+42] = 0x0000;
1612    // 13 CARD1                     0    //    fDataAC[i+106] = 0x0000;
1613    // 14 CAT1                      0    //   }
1614    // 15 CAS2                      0    for (UInt_t i=0; i<=7; i++){
1615    // 16 NC                        0          MSB      fDataAC[i+42] = evntLSB;
1616        fDataAC[i+106] = evntLSB;
1617    // In the first version only the hit-map is filled, not the SR.    };
1618    
1619    // Threshold: 0.8 MeV.    // increments for every trigger might be needed at some point.
1620      // dummy for now
1621    Float_t thr = 8e-4;    fDataAC[50]  = 0x0000;
1622      fDataAC[114] = 0x0000;
1623    fDataAC[3] = 0x0000;  
1624      // dummy FPGA clock (increment by 1 at each event)
1625    if (SumEcas[0] > thr)  fDataAC[3]  = 0x0004;    /*    
1626    if (SumEcas[1] > thr)  fDataAC[3] += 0x4000;      fDataAC[51] = 0x006C;
1627    if (SumEcas[2] > thr)  fDataAC[3] += 0x0400;      fDataAC[52] = 0x6C6C;
1628    if (SumEcas[3] > thr)  fDataAC[3] += 0x0040;        fDataAC[115] = 0x006C;
1629        fDataAC[116] = 0x6C6C;
1630    if (SumEcat[0] > thr)  fDataAC[3] += 0x2000;    */
1631    if (SumEcat[1] > thr)  fDataAC[3] += 0x0002;    if (Ievnt<=0xFFFF) {
1632    if (SumEcat[2] > thr)  fDataAC[3] += 0x0200;      fDataAC[51] = 0x0000;
1633    if (SumEcat[3] > thr)  fDataAC[3] += 0x0020;      fDataAC[52] = Ievnt;
1634          fDataAC[115] = 0x0000;
1635    if (SumEcard[0] > thr)  fDataAC[3] += 0x1000;      fDataAC[116] = Ievnt;
1636    if (SumEcard[1] > thr)  fDataAC[3] += 0x0010;    } else {
1637    if (SumEcard[2] > thr)  fDataAC[3] += 0x0100;      fDataAC[51] = evntMSB;
1638    if (SumEcard[3] > thr)  fDataAC[3] += 0x0001;      fDataAC[52] = evntLSB;
1639        fDataAC[115] = fDataAC[51];
1640    fDataAC[67] = fDataAC[3];      fDataAC[116] = fDataAC[52];
1641      }
1642    // shift registers  
1643    // the central bin is equal to the hitmap, all other bins in the shift register are 0    // dummy temperatures
1644    for (UInt_t i=0; i<=15; i++){    fDataAC[53] = 0x0000;
1645      fDataAC[i+11] = 0x0000;      fDataAC[54] = 0x0000;
1646      fDataAC[i+75] = 0x0000;    fDataAC[117] = 0x0000;
1647    }    fDataAC[118] = 0x0000;
1648    fDataAC[18] = fDataAC[3];  
1649    fDataAC[82] = fDataAC[3];  
1650      // dummy DAC thresholds
1651    //    for (Int_t i=0; i<fACbuffer; i++){    for (UInt_t i=0; i<=7; i++){
1652    //    printf("%0x  ",fDataAC[i]);        fDataAC[i+55] = 0x1A13;  
1653    //    if ((i+1)%8 ==0) cout << endl;      fDataAC[i+119] = 0x1A13;
1654    //   }    }
1655  };    
1656      // We activate all branches. Once the digitization algorithm is determined
1657      // only the branches that involve needed information will be activated
1658  void Digitizer::DigitizeS4(){    
1659    Int_t DEBUG=0;    fhBookTree->SetBranchAddress("Ievnt",&Ievnt);
1660    // creato:  S. Borisov, INFN Roma2 e MEPHI, Sett 2007    fhBookTree->SetBranchStatus("Nthcat",1);
1661    TString ciao,modo="ns";    fhBookTree->SetBranchStatus("Iparcat",1);
1662    Int_t i,j,t,NdF,pmt,NdFT,S4,S4v=0,S4p=32;    fhBookTree->SetBranchStatus("Icat",1);
1663    Float_t E0,E1=1e-6,Ert,X,Y,Z,x,y,z,V[3],Xs[2],Ys[2],Zs[2],Yp[6],q,w,p=0.1,l,l0=500;    fhBookTree->SetBranchStatus("Xincat",1);
1664    Xs[0]=-24.1;    fhBookTree->SetBranchStatus("Yincat",1);
1665    Xs[1]=24.1;    fhBookTree->SetBranchStatus("Zincat",1);
1666    Ys[0]=-24.1;    fhBookTree->SetBranchStatus("Xoutcat",1);
1667    Ys[1]=24.1;    fhBookTree->SetBranchStatus("Youtcat",1);
1668    Zs[0]=-0.5;    fhBookTree->SetBranchStatus("Zoutcat",1);
1669    Zs[1]=0.5;    fhBookTree->SetBranchStatus("Erelcat",1);
1670    Yp[0]=-20.;    fhBookTree->SetBranchStatus("Timecat",1);
1671    Yp[2]=-1.;    fhBookTree->SetBranchStatus("Pathcat",1);
1672    Yp[4]=17.;    fhBookTree->SetBranchStatus("P0cat",1);
1673    for(i=0;i<3;i++)    fhBookTree->SetBranchStatus("Nthcas",1);
1674      Yp[2*i+1]=Yp[2*i]+3;    fhBookTree->SetBranchStatus("Iparcas",1);
1675    srand(time(NULL));    fhBookTree->SetBranchStatus("Icas",1);
1676    // --- activate branches:    fhBookTree->SetBranchStatus("Xincas",1);
1677    fhBookTree->SetBranchStatus("Nthtof",1);    fhBookTree->SetBranchStatus("Yincas",1);
1678    fhBookTree->SetBranchStatus("Ipltof",1);    fhBookTree->SetBranchStatus("Zincas",1);
1679    fhBookTree->SetBranchStatus("Ipaddle",1);    fhBookTree->SetBranchStatus("Xoutcas",1);
1680        fhBookTree->SetBranchStatus("Youtcas",1);
1681    fhBookTree->SetBranchStatus("Xintof",1);    fhBookTree->SetBranchStatus("Zoutcas",1);
1682    fhBookTree->SetBranchStatus("Yintof",1);    fhBookTree->SetBranchStatus("Erelcas",1);
1683    fhBookTree->SetBranchStatus("Xouttof",1);    fhBookTree->SetBranchStatus("Timecas",1);
1684    fhBookTree->SetBranchStatus("Youttof",1);    fhBookTree->SetBranchStatus("Pathcas",1);
1685        fhBookTree->SetBranchStatus("P0cas",1);
1686    fhBookTree->SetBranchStatus("Ereltof",1);    fhBookTree->SetBranchStatus("Nthcard",1);
1687    fhBookTree->SetBranchStatus("Timetof",1);    fhBookTree->SetBranchStatus("Iparcard",1);
1688    NdFT=0;    fhBookTree->SetBranchStatus("Icard",1);
1689    Ert=0;    fhBookTree->SetBranchStatus("Xincard",1);
1690    for(i=0;i<Nthtof;i++){    fhBookTree->SetBranchStatus("Yincard",1);
1691      if(Ipltof[i]!=6) continue;    fhBookTree->SetBranchStatus("Zincard",1);
1692      Ert+=Ereltof[i];    fhBookTree->SetBranchStatus("Xoutcard",1);
1693                fhBookTree->SetBranchStatus("Youtcard",1);
1694      if(modo=="ns") continue;    fhBookTree->SetBranchStatus("Zoutcard",1);
1695      NdF=Int_t(Ereltof[i]/E1);    fhBookTree->SetBranchStatus("Erelcard",1);
1696      NdFT=0;    fhBookTree->SetBranchStatus("Timecard",1);
1697      X=Xintof[i];    fhBookTree->SetBranchStatus("Pathcard",1);
1698      Y=Yintof[i];    fhBookTree->SetBranchStatus("P0card",1);
1699      Z=(Float_t)(random())/(Float_t)(0x7fffffff)-0.5;  
1700      //cout<<"XYZ "<<X<<"  "<<Y<<"  "<<Z<<endl;    // In this simpliefied approach we will assume that once
1701      for(j=0;j<NdF;j++){    // a particle releases > 0.5 mip in one of the 12 AC detectors it
1702        q=(Float_t)random()/(Float_t)0x7fffffff;    // will fire. We will furthermore assume that both cards read out
1703        w=(Float_t)random()/(Float_t)0x7fffffff;    // identical data.
1704        // cout<<"qw "<<q<<" "<<w<<endl;  
1705        V[0]=p*cos(6.28318*q);    // If you develop your digitization algorithm, you should start by
1706        V[1]=p*sin(6.28318*q);    // identifying the information present in level2 (post-darth-vader)
1707        V[2]=p*(2.*w-1.);    // data.
1708        pmt=0;  
1709        x=X;    Float_t SumEcat[5];
1710        y=Y;    Float_t SumEcas[5];
1711        z=Z;    Float_t SumEcard[5];
1712        while(pmt==0 && (x>Xs[0] && x<Xs[1])&&(y>Ys[0] && y<Ys[1])&&(z>Zs[0] && z<Zs[1])){    for (Int_t k= 0;k<5;k++){
1713          l=0;      SumEcat[k]=0.;
1714          while(pmt==0 && (x>Xs[0] && x<Xs[1])&&(y>Ys[0] && y<Ys[1])&&(z>Zs[0] && z<Zs[1])){      SumEcas[k]=0.;
1715            x+=V[0];      SumEcard[k]=0.;
1716            y+=V[1];    };
1717            z+=V[2];  
1718            l+=p;    if (Nthcat>50 || Nthcas>50 || Nthcard>50)
1719            //cout<<x<<"  "<<y<<"  "<<z<<"  "<<l<<endl;      printf("*** ERROR AC! NthAC out of range!\n\n");
1720            //cin>>ciao;  
1721          }    // energy dependence on position (see file AcFitOutputDistancePmt.C by S.Orsi)
1722          if((x<Xs[0]+p || x>Xs[1]-p)&&(y>Ys[0]+p && y<Ys[1]-p)&&(z>Zs[0]+p && z<Zs[1]-p)){    // based on J.Lundquist's calculations (PhD thesis, page 94)
1723            for(t=0;t<3;t++){    // function: [0]+[1]*atan([2]/(x+1)), where the 3 parameters are:
1724              if(y>=Yp[2*t] && y<Yp[2*t+1]){    //   8.25470e-01   +- 1.79489e-02
1725                if(pmt==0)NdFT++;    //   6.41609e-01   +- 2.65846e-02
1726                pmt=1;    //   9.81177e+00   +- 1.21284e+00
1727                //cout<<NdFT<<endl;    // hp: 1 minimum ionising particle at 35cm from the PMT releases 1mip
1728                break;    //
1729              }    // NB: the PMT positions are needed!
1730            }  
1731            if(pmt==1)break;    // look in CAT
1732            V[0]=-V[0];    //  for (UInt_t k= 0;k<50;k++){
1733          }    for (Int_t k= 0;k<Nthcat;k++){
1734          q=(Float_t)random()/(Float_t)0x7fffffff;      if (Erelcat[k] > 0)
1735          w=1-exp(-l/l0);        SumEcat[Icat[k]] += Erelcat[k];
1736          if(q<w)break;    };
1737          q=(Float_t)random()/(Float_t)0x7fffffff;  
1738          w=0.5;    // look in CAS
1739          if(q<w)break;    for (Int_t k= 0;k<Nthcas;k++){
1740          if((x>Xs[0]+p && x<Xs[1]-p)&&(y<Ys[0]+p || y>Ys[1]-p)&&(z>Zs[0]+p && z<Zs[1]-p))V[1]=-V[1];      if (Erelcas[k] >0)
1741          if((x>Xs[0]+p && x<Xs[1]-p)&&(y>Ys[0]+p && y<Ys[1]-p)&&(z<Zs[0]+p || z>Zs[1]-p))V[2]=-V[2];        SumEcas[Icas[k]] += Erelcas[k];
1742          x+=V[0];    };
1743          y+=V[1];  
1744          z+=V[2];    // look in CARD
1745          l=0;    for (Int_t k= 0;k<Nthcard;k++){
1746          //cout<<x<<"  "<<y<<"  "<<z<<"  "<<l<<endl;      if (Erelcard[k] >0)
1747                  //cin>>ciao;        SumEcard[Icard[k]] += Erelcard[k];
1748        }    };
1749      }  
1750    }    // channel mapping              Hit Map
1751    Ert=Ert/0.002;    // 1 CARD4                      0          LSB
1752    q=(Float_t)(random())/(Float_t)0x7fffffff;    // 2 CAT2                       0
1753    w=0.7;    // 3 CAS1                       0
1754    //E0=(Float_t)(4064./7.);    // 4 NC                         0
1755    E0=4064./7.;    // 5 CARD2                      0
1756    if(Ert<1) S4=0;    // 6 CAT4                       1
1757    else S4=(Int_t)(4064.*(1.-exp(-(Ert-1.)/E0)));    // 7 CAS4                       0  
1758    i=S4/4;    // 8 NC                         0
1759    if(S4%4==0)    // 9 CARD3                      0
1760      S4v=S4+S4p;    // 10 CAT3                      0
1761    else if(S4%4==1){    // 11 CAS3                      0
1762      if(q<w) S4v=S4-1+S4p;    // 12 NC                        0
1763      else S4v=S4+1+S4p;    // 13 CARD1                     0
1764    } else if(S4%4==2) S4v=S4+S4p;    // 14 CAT1                      0
1765    else if(S4%4==3){    // 15 CAS2                      0
1766      if(q<w) S4v=S4+1+S4p;    // 16 NC                        0          MSB
1767      else S4v=S4-1+S4p;  
1768    }    // In the first version only the hit-map is filled, not the SR.
1769    if (DEBUG)  
1770      cout<<"Ert_S4 = " << Ert << " --- S4v = " << S4v << endl;    // Threshold: 0.8 MeV.
1771    fDataS4[0]=S4v;//0xf028;  
1772    fDataS4[1]=0xd800;    Float_t thr = 8e-4;
1773    fDataS4[2]=0x0300;  
1774    //cout<<"  PMT  "<<NdFT<<"  "<<NdF<<endl;    fDataAC[3] = 0x0000;
1775    //cin>>ciao;  
1776  }    if (SumEcas[0] > thr)  fDataAC[3]  = 0x0004;
1777      if (SumEcas[1] > thr)  fDataAC[3] += 0x4000;
1778      if (SumEcas[2] > thr)  fDataAC[3] += 0x0400;
1779      if (SumEcas[3] > thr)  fDataAC[3] += 0x0040;  
1780  void Digitizer::DigitizeND(){  
1781    // creato:  S. Borisov, INFN Roma2 e MEPHI, Sett 2007    if (SumEcat[0] > thr)  fDataAC[3] += 0x2000;
1782    Int_t i=0;    if (SumEcat[1] > thr)  fDataAC[3] += 0x0002;
1783    UShort_t NdN=0;    if (SumEcat[2] > thr)  fDataAC[3] += 0x0200;
1784    fhBookTree->SetBranchStatus("Nthnd",1);    if (SumEcat[3] > thr)  fDataAC[3] += 0x0020;
1785    fhBookTree->SetBranchStatus("Itubend",1);    
1786    fhBookTree->SetBranchStatus("Iparnd",1);      if (SumEcard[0] > thr)  fDataAC[3] += 0x1000;
1787    fhBookTree->SetBranchStatus("Xinnd",1);    if (SumEcard[1] > thr)  fDataAC[3] += 0x0010;
1788    fhBookTree->SetBranchStatus("Yinnd",1);    if (SumEcard[2] > thr)  fDataAC[3] += 0x0100;
1789    fhBookTree->SetBranchStatus("Zinnd",1);    if (SumEcard[3] > thr)  fDataAC[3] += 0x0001;
1790    fhBookTree->SetBranchStatus("Xoutnd",1);  
1791    fhBookTree->SetBranchStatus("Youtnd",1);    fDataAC[67] = fDataAC[3];
1792    fhBookTree->SetBranchStatus("Zoutnd",1);  
1793    fhBookTree->SetBranchStatus("Erelnd",1);    // shift registers
1794    fhBookTree->SetBranchStatus("Timend",1);    // the central bin is equal to the hitmap, all other bins in the shift register are 0
1795    fhBookTree->SetBranchStatus("Pathnd",1);    for (UInt_t i=0; i<=15; i++){
1796    fhBookTree->SetBranchStatus("P0nd",1);      fDataAC[i+11] = 0x0000;  
1797    //cout<<"n="<<Nthnd<<"  "<<NdN<<"\n";      fDataAC[i+75] = 0x0000;
1798    for(i=0;i<Nthnd;i++){    }
1799      if(Iparnd[i]==13){    fDataAC[18] = fDataAC[3];
1800        NdN++;    fDataAC[82] = fDataAC[3];
1801      }  
1802    }    //    for (Int_t i=0; i<fACbuffer; i++){
1803    //NdN=100; //only for debug    //    printf("%0x  ",fDataAC[i]);  
1804      //    if ((i+1)%8 ==0) cout << endl;
1805    for(i=0;i<3;i++){    //   }
1806      fDataND[2*i]=0x0000;  };
1807      fDataND[2*i+1]=0x010F;  
1808    }  
1809    fDataND[0]=0xFF00 & (256*NdN);  void Digitizer::DigitizeS4(){
1810  }    Int_t DEBUG=0;
1811      // creato:  S. Borisov, INFN Roma2 e MEPHI, Sett 2007
1812      TString ciao,modo="ns";
1813  void Digitizer::DigitizeDummy() {    Int_t i,j,t,NdF,pmt,NdFT,S4,S4v=0,S4p=32;
1814      Float_t E0,E1=1e-6,Ert,X,Y,Z,x,y,z,V[3],Xs[2],Ys[2],Zs[2],Yp[6],q,w,p=0.1,l,l0=500;
1815    fhBookTree->SetBranchStatus("Enestrip",1);    Xs[0]=-24.1;
1816      Xs[1]=24.1;
1817    // dumy header    Ys[0]=-24.1;
1818    fDataDummy[0] = 0xCAAA;    Ys[1]=24.1;
1819      Zs[0]=-0.5;
1820    for (Int_t i=1; i<fDummybuffer; i++){    Zs[1]=0.5;
1821      fDataDummy[i] = 0xFFFF;    Yp[0]=-20.;
1822      //   printf("%0x  ",fDataDummy[i]);      Yp[2]=-1.;
1823      //if ((i+1)%8 ==0) cout << endl;    Yp[4]=17.;
1824    }    for(i=0;i<3;i++)
1825  };      Yp[2*i+1]=Yp[2*i]+3;
1826      srand(time(NULL));
1827      // --- activate branches:
1828  void Digitizer::WriteData(){    fhBookTree->SetBranchStatus("Nthtof",1);
1829      fhBookTree->SetBranchStatus("Ipltof",1);
1830    // Routine that writes the data to a binary file    fhBookTree->SetBranchStatus("Ipaddle",1);
1831    // PSCU data are already swapped    
1832    fOutputfile.write(reinterpret_cast<char*>(fDataPSCU),sizeof(UShort_t)*fPSCUbuffer);    fhBookTree->SetBranchStatus("Xintof",1);
1833    // TRG    fhBookTree->SetBranchStatus("Yintof",1);
1834    fOutputfile.write(reinterpret_cast<char*>(fDataTrigger),sizeof(UChar_t)*153);    fhBookTree->SetBranchStatus("Xouttof",1);
1835    // TOF    fhBookTree->SetBranchStatus("Youttof",1);
1836    fOutputfile.write(reinterpret_cast<char*>(fDataTof),sizeof(UChar_t)*276);    
1837    // AC    fhBookTree->SetBranchStatus("Ereltof",1);
1838    UShort_t temp[1000000];    fhBookTree->SetBranchStatus("Timetof",1);
1839    memset(temp,0,sizeof(UShort_t)*1000000);    NdFT=0;
1840    swab(fDataAC,temp,sizeof(UShort_t)*fACbuffer);  // WE MUST SWAP THE BYTES!!!    Ert=0;
1841    fOutputfile.write(reinterpret_cast<char*>(temp),sizeof(UShort_t)*fACbuffer);    for(i=0;i<Nthtof;i++){
1842    // CALO      if(Ipltof[i]!=6) continue;
1843    memset(temp,0,sizeof(UShort_t)*1000000);      Ert+=Ereltof[i];
1844    swab(fDataCALO,temp,sizeof(UShort_t)*fCALOlength); // WE MUST SWAP THE BYTES!!!            
1845    fOutputfile.write(reinterpret_cast<char*>(temp),sizeof(UShort_t)*fCALOlength);      if(modo=="ns") continue;
1846    // TRK      NdF=Int_t(Ereltof[i]/E1);
1847    memset(temp,0,sizeof(UShort_t)*1000000);      NdFT=0;
1848    swab(fDataTrack,temp,sizeof(UShort_t)*fTracklength);  // WE MUST SWAP THE BYTES!!!      X=Xintof[i];
1849    fOutputfile.write(reinterpret_cast<char*>(temp),sizeof(UShort_t)*fTracklength);      Y=Yintof[i];
1850    fTracklength=0;      Z=(Float_t)(random())/(Float_t)(0x7fffffff)-0.5;
1851     // padding to 64 bytes      //cout<<"XYZ "<<X<<"  "<<Y<<"  "<<Z<<endl;
1852    //      for(j=0;j<NdF;j++){
1853    if ( fPadding ){        q=(Float_t)random()/(Float_t)0x7fffffff;
1854      fOutputfile.write(reinterpret_cast<char*>(fDataPadding),sizeof(UChar_t)*fPadding);        w=(Float_t)random()/(Float_t)0x7fffffff;
1855    };        // cout<<"qw "<<q<<" "<<w<<endl;
1856    // S4        V[0]=p*cos(6.28318*q);
1857    memset(temp,0,sizeof(UShort_t)*1000000);        V[1]=p*sin(6.28318*q);
1858    swab(fDataS4,temp,sizeof(UShort_t)*fS4buffer);  // WE MUST SWAP THE BYTES!!!        V[2]=p*(2.*w-1.);
1859    fOutputfile.write(reinterpret_cast<char*>(temp),sizeof(UShort_t)*fS4buffer);        pmt=0;
1860    // ND        x=X;
1861    memset(temp,0,sizeof(UShort_t)*1000000);        y=Y;
1862    swab(fDataND,temp,sizeof(UShort_t)*fNDbuffer);  // WE MUST SWAP THE BYTES!!!        z=Z;
1863    fOutputfile.write(reinterpret_cast<char*>(temp),sizeof(UShort_t)*fNDbuffer);        while(pmt==0 && (x>Xs[0] && x<Xs[1])&&(y>Ys[0] && y<Ys[1])&&(z>Zs[0] && z<Zs[1])){
1864  };          l=0;
1865            while(pmt==0 && (x>Xs[0] && x<Xs[1])&&(y>Ys[0] && y<Ys[1])&&(z>Zs[0] && z<Zs[1])){
1866              x+=V[0];
1867  void Digitizer::ReadData(){            y+=V[1];
1868              z+=V[2];
1869    UShort_t InData[64];            l+=p;
1870              //cout<<x<<"  "<<y<<"  "<<z<<"  "<<l<<endl;
1871    // for debuggigng purposes only, write your own routine if you like (many            //cin>>ciao;
1872    // hardwired things.          }
1873              if((x<Xs[0]+p || x>Xs[1]-p)&&(y>Ys[0]+p && y<Ys[1]-p)&&(z>Zs[0]+p && z<Zs[1]-p)){
1874    ifstream InputFile;            for(t=0;t<3;t++){
1875                if(y>=Yp[2*t] && y<Yp[2*t+1]){
1876    // if (!InputFile) {                if(pmt==0)NdFT++;
1877                  pmt=1;
1878    //     std::cout << "ERROR" << endl;                //cout<<NdFT<<endl;
1879    //     // An error occurred!                break;
1880    //     // myFile.gcount() returns the number of bytes read.              }
1881    //     // calling myFile.clear() will reset the stream state            }
1882    //     // so it is usable again.            if(pmt==1)break;
1883    //   };            V[0]=-V[0];
1884            }
1885            q=(Float_t)random()/(Float_t)0x7fffffff;
1886              w=1-exp(-l/l0);
1887    //InputFile.seekg(0);          if(q<w)break;
1888            q=(Float_t)random()/(Float_t)0x7fffffff;
1889    InputFile.open(fFilename, ios::in | ios::binary);          w=0.5;
1890    //    fOutputfile.seekg(0);          if(q<w)break;
1891    if (!InputFile.is_open()) std::cout << "ERROR" << endl;          if((x>Xs[0]+p && x<Xs[1]-p)&&(y<Ys[0]+p || y>Ys[1]-p)&&(z>Zs[0]+p && z<Zs[1]-p))V[1]=-V[1];
1892            if((x>Xs[0]+p && x<Xs[1]-p)&&(y>Ys[0]+p && y<Ys[1]-p)&&(z<Zs[0]+p || z>Zs[1]-p))V[2]=-V[2];
1893    InputFile.seekg(0);          x+=V[0];
1894              y+=V[1];
1895    for (Int_t k=0; k<=1000; k++){          z+=V[2];
1896      InputFile.read(reinterpret_cast<char*>(InData),384*sizeof(UShort_t));          l=0;
1897            //cout<<x<<"  "<<y<<"  "<<z<<"  "<<l<<endl;
1898      std::cout << "Read back: " << endl << endl;                  //cin>>ciao;
1899          }
1900      for (Int_t i=0; i<=384; i++){      }
1901        printf("%4x ", InData[i]);      }
1902        if ((i+1)%8 ==0) cout << endl;    Ert=Ert/0.002;
1903      }    q=(Float_t)(random())/(Float_t)0x7fffffff;
1904      w=0.7;
1905    }    //E0=(Float_t)(4064./7.);
1906    cout << endl;    E0=4064./7.;
1907    InputFile.close();    if(Ert<1) S4=0;
1908      else S4=(Int_t)(4064.*(1.-exp(-(Ert-1.)/E0)));
1909  };    i=S4/4;
1910      if(S4%4==0)
1911        S4v=S4+S4p;
1912      else if(S4%4==1){
1913  void Digitizer::DigitizeTrack() {      if(q<w) S4v=S4-1+S4p;
1914  //std:: cout << "Entering DigitizeTrack " << endl;      else S4v=S4+1+S4p;
1915  Float_t  AdcTrack[fNviews][fNstrips_view];  //  Vector of strips to be compressed    } else if(S4%4==2) S4v=S4+S4p;
1916      else if(S4%4==3){
1917  Int_t Iview;      if(q<w) S4v=S4+1+S4p;
1918  Int_t Nstrip;      else S4v=S4-1+S4p;
1919      }
1920    for (Int_t j=0; j<fNviews;j++) {    if (DEBUG)
1921        cout<<"Ert_S4 = " << Ert << " --- S4v = " << S4v << endl;
1922      for (Int_t i=0; i<fNladder;i++) {    fDataS4[0]=S4v;//0xf028;
1923      fDataS4[1]=0xd800;
1924        Float_t commonN1=gRandom->Gaus(0.,fSigmaCommon);    fDataS4[2]=0x0300;
1925        Float_t commonN2=gRandom->Gaus(0.,fSigmaCommon);    //cout<<"  PMT  "<<NdFT<<"  "<<NdF<<endl;
1926        for (Int_t k=0; k<fNstrips_ladder;k++) {    //cin>>ciao;
1927        Nstrip=i*fNstrips_ladder+k;  }
1928        AdcTrack[j][Nstrip]=gRandom->Gaus(fPedeTrack[j][Nstrip],fSigmaTrack[j][Nstrip]);  
1929        if(k<4*128) {AdcTrack[j][Nstrip] += commonN1;}  // full correlation of 4 VA1 Com. Noise  
1930        else {AdcTrack[j][Nstrip] += commonN2;}   // full correlation of 4 VA1 Com. Noise  
1931    void Digitizer::DigitizeND(){
1932        };    // creato:  S. Borisov, INFN Roma2 e MEPHI, Sett 2007
1933            Int_t i=0;
1934              UShort_t NdN=0;
1935      };    fhBookTree->SetBranchStatus("Nthnd",1);
1936      fhBookTree->SetBranchStatus("Itubend",1);
1937      fhBookTree->SetBranchStatus("Iparnd",1);  
1938    };    fhBookTree->SetBranchStatus("Xinnd",1);
1939      fhBookTree->SetBranchStatus("Yinnd",1);
1940      fhBookTree->SetBranchStatus("Zinnd",1);
1941    fhBookTree->SetBranchStatus("Nstrpx",1);    fhBookTree->SetBranchStatus("Xoutnd",1);
1942    fhBookTree->SetBranchStatus("Npstripx",1);    fhBookTree->SetBranchStatus("Youtnd",1);
1943    fhBookTree->SetBranchStatus("Ntstripx",1);    fhBookTree->SetBranchStatus("Zoutnd",1);
1944    fhBookTree->SetBranchStatus("Istripx",1);    fhBookTree->SetBranchStatus("Erelnd",1);
1945    fhBookTree->SetBranchStatus("Qstripx",1);    fhBookTree->SetBranchStatus("Timend",1);
1946    fhBookTree->SetBranchStatus("Xstripx",1);    fhBookTree->SetBranchStatus("Pathnd",1);
1947    fhBookTree->SetBranchStatus("Nstrpy",1);    fhBookTree->SetBranchStatus("P0nd",1);
1948    fhBookTree->SetBranchStatus("Npstripy",1);    //cout<<"n="<<Nthnd<<"  "<<NdN<<"\n";
1949    fhBookTree->SetBranchStatus("Ntstripy",1);    for(i=0;i<Nthnd;i++){
1950    fhBookTree->SetBranchStatus("Istripy",1);      if(Iparnd[i]==13){
1951    fhBookTree->SetBranchStatus("Qstripy",1);        NdN++;
1952    fhBookTree->SetBranchStatus("Ystripy",1);      }
1953      }
1954      //NdN=100; //only for debug
1955    
1956    Float_t ADCfull;    for(i=0;i<3;i++){
1957    Int_t iladd=0;      fDataND[2*i]=0x0000;
1958    for (Int_t ix=0; ix<Nstrpx;ix++) {      fDataND[2*i+1]=0x010F;
1959    Iview=Npstripx[ix]*2-1;    }
1960    Nstrip=(Int_t)Istripx[ix]-1;    fDataND[0]=0xFF00 & (256*NdN);
1961    if(Nstrip<fNstrips_ladder) iladd=0;  }
1962    if((Nstrip>=fNstrips_ladder)&&(Nstrip<2*fNstrips_ladder)) iladd=1;  
1963    if((Nstrip>=2*fNstrips_ladder)&&(Nstrip<3*fNstrips_ladder)) iladd=2;  
1964    ADCfull=AdcTrack[Iview][Nstrip] += Qstripx[ix]*fMipCor[iladd][Iview];  void Digitizer::DigitizeDummy() {
1965    AdcTrack[Iview][Nstrip] *= SaturationTrack(ADCfull);  
1966      fhBookTree->SetBranchStatus("Enestrip",1);
1967    };  
1968      // dumy header
1969      fDataDummy[0] = 0xCAAA;
1970    for (Int_t iy=0; iy<Nstrpy;iy++) {  
1971    Iview=Npstripy[iy]*2-2;    for (Int_t i=1; i<fDummybuffer; i++){
1972    Nstrip=(Int_t)Istripy[iy]-1;      fDataDummy[i] = 0xFFFF;
1973    if(Nstrip<fNstrips_ladder) iladd=0;      //   printf("%0x  ",fDataDummy[i]);  
1974    if((Nstrip>=fNstrips_ladder)&&(Nstrip<2*fNstrips_ladder)) iladd=1;      //if ((i+1)%8 ==0) cout << endl;
1975    if((Nstrip>=2*fNstrips_ladder)&&(Nstrip<3*fNstrips_ladder)) iladd=2;    }
1976    ADCfull=AdcTrack[Iview][Nstrip] -= Qstripy[iy]*fMipCor[iladd][Iview];  };
1977    AdcTrack[Iview][Nstrip] *= SaturationTrack(ADCfull);  
1978    
1979    };    void Digitizer::WriteData(){
1980          
1981  CompressTrackData(AdcTrack);  // Compress and Digitize data of one Ladder  in turn for all ladders    // Routine that writes the data to a binary file
1982      // PSCU data are already swapped
1983  };    fOutputfile.write(reinterpret_cast<char*>(fDataPSCU),sizeof(UShort_t)*fPSCUbuffer);
1984      // TRG
1985      fOutputfile.write(reinterpret_cast<char*>(fDataTrigger),sizeof(UChar_t)*153);
1986      // TOF
1987  void Digitizer::DigitizeTrackCalib(Int_t ii) {    fOutputfile.write(reinterpret_cast<char*>(fDataTof),sizeof(UChar_t)*276);
1988      // AC
1989  std:: cout << "Entering DigitizeTrackCalib " << ii << endl;    UShort_t temp[1000000];
1990  if( (ii!=1)&&(ii!=2) ) {    memset(temp,0,sizeof(UShort_t)*1000000);
1991   std:: cout << "error wrong DigitizeTrackCalib argument" << endl;    swab(fDataAC,temp,sizeof(UShort_t)*fACbuffer);  // WE MUST SWAP THE BYTES!!!
1992   return;    fOutputfile.write(reinterpret_cast<char*>(temp),sizeof(UShort_t)*fACbuffer);
1993  };    // CALO
1994      memset(temp,0,sizeof(UShort_t)*1000000);
1995  memset(fDataTrack,0,sizeof(UShort_t)*fTRACKbuffer);    swab(fDataCALO,temp,sizeof(UShort_t)*fCALOlength); // WE MUST SWAP THE BYTES!!!
1996  fTracklength=0;    fOutputfile.write(reinterpret_cast<char*>(temp),sizeof(UShort_t)*fCALOlength);
1997      // TRK
1998  UShort_t Dato;    memset(temp,0,sizeof(UShort_t)*1000000);
1999      swab(fDataTrack,temp,sizeof(UShort_t)*fTracklength);  // WE MUST SWAP THE BYTES!!!
2000  Float_t dato1;    fOutputfile.write(reinterpret_cast<char*>(temp),sizeof(UShort_t)*fTracklength);
2001  Float_t dato2;    fTracklength=0;
2002  Float_t dato3;     // padding to 64 bytes
2003  Float_t dato4;    //
2004      if ( fPadding ){
2005  UShort_t DatoDec;      fOutputfile.write(reinterpret_cast<char*>(fDataPadding),sizeof(UChar_t)*fPadding);
2006  UShort_t DatoDec1;    };
2007  UShort_t DatoDec2;    // S4
2008  UShort_t DatoDec3;    memset(temp,0,sizeof(UShort_t)*1000000);
2009  UShort_t DatoDec4;    swab(fDataS4,temp,sizeof(UShort_t)*fS4buffer);  // WE MUST SWAP THE BYTES!!!
2010      fOutputfile.write(reinterpret_cast<char*>(temp),sizeof(UShort_t)*fS4buffer);
2011  UShort_t EVENT_CAL;    // ND
2012  UShort_t PED_L1;    memset(temp,0,sizeof(UShort_t)*1000000);
2013  UShort_t ReLength;    swab(fDataND,temp,sizeof(UShort_t)*fNDbuffer);  // WE MUST SWAP THE BYTES!!!
2014  UShort_t OveCheckCode;    fOutputfile.write(reinterpret_cast<char*>(temp),sizeof(UShort_t)*fNDbuffer);
2015  //UShort_t PED_L2;  };
2016  //UShort_t PED_L3HI;  
2017  //UShort_t PED_L3LO;  
2018  //UShort_t SIG_L1HI;  void Digitizer::ReadData(){
2019  //UShort_t SIG_L1LO;  
2020  //UShort_t SIG_L2HI;    UShort_t InData[64];
2021  //UShort_t SIG_L2LO;  
2022  //UShort_t SIG_L3;    // for debuggigng purposes only, write your own routine if you like (many
2023  //UShort_t BAD_L1;    // hardwired things.
2024  //UShort_t BAD_L2LO;    
2025  //UShort_t BAD_L3HI;    ifstream InputFile;
2026  //UShort_t BAD_L3LO;  
2027  //UShort_t FLAG;    // if (!InputFile) {
2028    
2029      //     std::cout << "ERROR" << endl;
2030    Int_t DSPpos;    //     // An error occurred!
2031    for (Int_t j=ii-1; j<fNviews;j+=2) {    //     // myFile.gcount() returns the number of bytes read.
2032    UShort_t CkSum=0;    //     // calling myFile.clear() will reset the stream state
2033    // here skip the dsp header and his trailer , to be written later    //     // so it is usable again.
2034    DSPpos=fTracklength;    //   };
2035    fTracklength=fTracklength+13+3;  
2036    
2037      
2038      for (Int_t i=0; i<fNladder;i++) {    //InputFile.seekg(0);
2039        for (Int_t k=0; k<fNstrips_ladder;k++) {  
2040        // write in buffer the current LADDER    InputFile.open(fFilename, ios::in | ios::binary);
2041        Dato=(UShort_t)fPedeTrack[j][i*fNstrips_ladder+k];    //    fOutputfile.seekg(0);
2042        dato1=fPedeTrack[j][i*fNstrips_ladder+k]-Dato;    if (!InputFile.is_open()) std::cout << "ERROR" << endl;
2043    
2044        DatoDec1=(UShort_t)(dato1*2);    InputFile.seekg(0);
2045        dato2=dato1*2-DatoDec1;    
2046      for (Int_t k=0; k<=1000; k++){
2047        DatoDec2=(UShort_t)(dato2*2);      InputFile.read(reinterpret_cast<char*>(InData),384*sizeof(UShort_t));
2048        dato3=dato2*2-DatoDec2;  
2049              std::cout << "Read back: " << endl << endl;
2050        DatoDec3=(UShort_t)(dato3*2);  
2051        dato4=dato3*2-DatoDec3;      for (Int_t i=0; i<=384; i++){
2052                printf("%4x ", InData[i]);  
2053        DatoDec4=(UShort_t)(dato4*2);        if ((i+1)%8 ==0) cout << endl;
2054              }
2055        DatoDec=DatoDec1*0x0008+DatoDec2*0x0004+DatoDec3*0x0002+DatoDec4*0x0001;  
2056        fDataTrack[fTracklength]=( (Dato << 4) | (DatoDec & 0x000F) );    }
2057        CkSum=CkSum^fDataTrack[fTracklength];    cout << endl;
2058        fTracklength++;    InputFile.close();
2059        };  
2060    };
2061        for (Int_t k=0; k<fNstrips_ladder;k++) {  
2062        // write in buffer the current LADDER  
2063        Dato=(UShort_t)fSigmaTrack[j][i*fNstrips_ladder+k];  
2064        dato1=fSigmaTrack[j][i*fNstrips_ladder+k]-Dato;  void Digitizer::DigitizeTrack() {
2065    //std:: cout << "Entering DigitizeTrack " << endl;
2066        DatoDec1=(UShort_t)(dato1*2);  Float_t  AdcTrack[fNviews][fNstrips_view];  //  Vector of strips to be compressed
2067        dato2=dato1*2-DatoDec1;  
2068    Int_t Iview;
2069        DatoDec2=(UShort_t)(dato2*2);  Int_t Nstrip;
2070        dato3=dato2*2-DatoDec2;  
2071            for (Int_t j=0; j<fNviews;j++) {
2072        DatoDec3=(UShort_t)(dato3*2);  
2073        dato4=dato3*2-DatoDec3;      for (Int_t i=0; i<fNladder;i++) {
2074          
2075        DatoDec4=(UShort_t)(dato4*2);        Float_t commonN1=gRandom->Gaus(0.,fSigmaCommon);
2076                Float_t commonN2=gRandom->Gaus(0.,fSigmaCommon);
2077        DatoDec=DatoDec1*0x0008+DatoDec2*0x0004+DatoDec3*0x0002+DatoDec4*0x0001;        for (Int_t k=0; k<fNstrips_ladder;k++) {
2078                Nstrip=i*fNstrips_ladder+k;
2079        fDataTrack[fTracklength]=( (Dato << 4) | (DatoDec & 0x000F) );        AdcTrack[j][Nstrip]=gRandom->Gaus(fPedeTrack[j][Nstrip],fSigmaTrack[j][Nstrip]);
2080        CkSum=CkSum^fDataTrack[fTracklength];        if(k<4*128) {AdcTrack[j][Nstrip] += commonN1;}  // full correlation of 4 VA1 Com. Noise
2081        fTracklength++;        else {AdcTrack[j][Nstrip] += commonN2;}   // full correlation of 4 VA1 Com. Noise
2082        };  
2083                };
2084        for (Int_t k=0; k<64;k++) {        
2085        fDataTrack[fTracklength]=0x0000;          
2086        CkSum=CkSum^fDataTrack[fTracklength];      };
2087        fTracklength++;  
2088    
2089        };    };
2090        // end ladder  
2091    
2092      // write in buffer the end ladder word    fhBookTree->SetBranchStatus("Nstrpx",1);
2093      if(i==0) fDataTrack[fTracklength]=0x1807;    fhBookTree->SetBranchStatus("Npstripx",1);
2094      if(i==1) fDataTrack[fTracklength]=0x1808;    fhBookTree->SetBranchStatus("Ntstripx",1);
2095      if(i==2) fDataTrack[fTracklength]=0x1809;    fhBookTree->SetBranchStatus("Istripx",1);
2096      CkSum=CkSum^fDataTrack[fTracklength];    fhBookTree->SetBranchStatus("Qstripx",1);
2097      fTracklength++;    fhBookTree->SetBranchStatus("Xstripx",1);
2098      fhBookTree->SetBranchStatus("Nstrpy",1);
2099      // write in buffer the TRAILER    fhBookTree->SetBranchStatus("Npstripy",1);
2100      ReLength=(UShort_t)((fNstrips_ladder*2+64+1)*2+3);    fhBookTree->SetBranchStatus("Ntstripy",1);
2101      OveCheckCode=0x0000;    fhBookTree->SetBranchStatus("Istripy",1);
2102      fhBookTree->SetBranchStatus("Qstripy",1);
2103      fDataTrack[fTracklength]=0x0000;    fhBookTree->SetBranchStatus("Ystripy",1);
2104      fTracklength++;  
2105      
2106      fDataTrack[fTracklength]=(ReLength >> 8);  
2107      fTracklength++;    Float_t ADCfull;
2108        Int_t iladd=0;
2109      fDataTrack[fTracklength]=( (ReLength << 8) | (OveCheckCode & 0x00FF) );    for (Int_t ix=0; ix<Nstrpx;ix++) {
2110      fTracklength++;    Iview=Npstripx[ix]*2-1;
2111      Nstrip=(Int_t)Istripx[ix]-1;
2112      // end TRAILER            if(Nstrip<fNstrips_ladder) iladd=0;
2113      };    if((Nstrip>=fNstrips_ladder)&&(Nstrip<2*fNstrips_ladder)) iladd=1;
2114      if((Nstrip>=2*fNstrips_ladder)&&(Nstrip<3*fNstrips_ladder)) iladd=2;
2115    // write in buffer the DSP header    ADCfull=AdcTrack[Iview][Nstrip] += Qstripx[ix]*fMipCor[iladd][Iview];
2116      AdcTrack[Iview][Nstrip] *= SaturationTrack(ADCfull);
2117    fDataTrack[DSPpos]=(0xE800 | ( ((j+1) << 3) | 0x0005) );  
2118        };
2119    fDataTrack[DSPpos+1]=0x01A9;  
2120    
2121    fDataTrack[DSPpos+2]=0x8740;    for (Int_t iy=0; iy<Nstrpy;iy++) {
2122        Iview=Npstripy[iy]*2-2;
2123    EVENT_CAL=0;    Nstrip=(Int_t)Istripy[iy]-1;
2124    fDataTrack[DSPpos+3]=(0x1A00 | ( (0x03FF & EVENT_CAL)>> 1) );    if(Nstrip<fNstrips_ladder) iladd=0;
2125        if((Nstrip>=fNstrips_ladder)&&(Nstrip<2*fNstrips_ladder)) iladd=1;
2126    PED_L1=0;    if((Nstrip>=2*fNstrips_ladder)&&(Nstrip<3*fNstrips_ladder)) iladd=2;
2127    fDataTrack[DSPpos+4]=( ((EVENT_CAL << 15) | 0x5002 ) | ((0x03FF & PED_L1) << 2) );    ADCfull=AdcTrack[Iview][Nstrip] -= Qstripy[iy]*fMipCor[iladd][Iview];
2128        AdcTrack[Iview][Nstrip] *= SaturationTrack(ADCfull);
2129    // FROM HERE WE WRITE AS ALL VARIABLE apart CkSum are =0    
2130      };  
2131    fDataTrack[DSPpos+5]=0x8014;        
2132      CompressTrackData(AdcTrack);  // Compress and Digitize data of one Ladder  in turn for all ladders
2133    fDataTrack[DSPpos+6]=0x00A0;  
2134      };
2135    fDataTrack[DSPpos+7]=0x0500;  
2136      
2137    fDataTrack[DSPpos+8]=0x2801;  
2138      void Digitizer::DigitizeTrackCalib(Int_t ii) {
2139    fDataTrack[DSPpos+9]=0x400A;  
2140      std:: cout << "Entering DigitizeTrackCalib " << ii << endl;
2141    fDataTrack[DSPpos+10]=0x0050;  if( (ii!=1)&&(ii!=2) ) {
2142       std:: cout << "error wrong DigitizeTrackCalib argument" << endl;
2143    CkSum=(CkSum >> 8)^(CkSum&0x00FF);   return;
2144    fDataTrack[DSPpos+11]=(0x0280 | (CkSum >> 3));  };
2145      
2146    fDataTrack[DSPpos+12]=(0x1FFF | (CkSum << 13) );  memset(fDataTrack,0,sizeof(UShort_t)*fTRACKbuffer);
2147    fTracklength=0;
2148    // end dsp header  
2149    UShort_t Dato;
2150    // write in buffer the TRAILER  
2151      Float_t dato1;
2152    ReLength=(UShort_t)((13*2)+3);  Float_t dato2;
2153    OveCheckCode=0x0000;  Float_t dato3;
2154    fDataTrack[DSPpos+13]=0x0000;  Float_t dato4;
2155    
2156    fDataTrack[DSPpos+14]=(ReLength >> 8);  UShort_t DatoDec;
2157      UShort_t DatoDec1;
2158    fDataTrack[DSPpos+15]=( (ReLength << 8) | (OveCheckCode & 0x00FF) );  UShort_t DatoDec2;
2159      UShort_t DatoDec3;
2160    // end TRAILER  UShort_t DatoDec4;
2161    
2162    UShort_t EVENT_CAL;
2163    UShort_t PED_L1;
2164      UShort_t ReLength;
2165    // end DSP      UShort_t OveCheckCode;
2166    };      //UShort_t PED_L2;
2167    //UShort_t PED_L3HI;
2168    //UShort_t PED_L3LO;
2169    //UShort_t SIG_L1HI;
2170  };  //UShort_t SIG_L1LO;
2171    //UShort_t SIG_L2HI;
2172  void Digitizer::WriteTrackCalib() {  //UShort_t SIG_L2LO;
2173    //UShort_t SIG_L3;
2174    //UShort_t BAD_L1;
2175  std:: cout << " Entering WriteTrackCalib " << endl;  //UShort_t BAD_L2LO;
2176    //UShort_t BAD_L3HI;
2177  fOutputfile.write(reinterpret_cast<char*>(fDataPSCU),sizeof(UShort_t)*fPSCUbuffer);  //UShort_t BAD_L3LO;
2178    //UShort_t FLAG;
2179  UShort_t temp[1000000];  
2180  memset(temp,0,sizeof(UShort_t)*1000000);  
2181  swab(fDataTrack,temp,sizeof(UShort_t)*fTracklength);  // WE MUST SWAP THE BYTES!!!    Int_t DSPpos;
2182  fOutputfile.write(reinterpret_cast<char*>(temp),sizeof(UShort_t)*fTracklength);    for (Int_t j=ii-1; j<fNviews;j+=2) {
2183  fTracklength=0;    UShort_t CkSum=0;
2184  if ( fPadding ){    // here skip the dsp header and his trailer , to be written later
2185        fOutputfile.write(reinterpret_cast<char*>(fDataPadding),sizeof(UChar_t)*fPadding);    DSPpos=fTracklength;
2186  };    fTracklength=fTracklength+13+3;
2187    
2188  };  
2189        for (Int_t i=0; i<fNladder;i++) {
2190          for (Int_t k=0; k<fNstrips_ladder;k++) {
2191  void Digitizer::ClearTrackCalib() {        // write in buffer the current LADDER
2192          Dato=(UShort_t)fPedeTrack[j][i*fNstrips_ladder+k];
2193  std:: cout << "Entering ClearTrackCalib " << endl;        dato1=fPedeTrack[j][i*fNstrips_ladder+k]-Dato;
2194        
2195            DatoDec1=(UShort_t)(dato1*2);
2196  };        dato2=dato1*2-DatoDec1;
2197    
2198          DatoDec2=(UShort_t)(dato2*2);
2199  void Digitizer::LoadTrackCalib() {        dato3=dato2*2-DatoDec2;
2200  std:: cout << "Entering LoadTrackCalib " << endl;        
2201          DatoDec3=(UShort_t)(dato3*2);
2202  // Generate the pedestals and sigmas according to parametrization        dato4=dato3*2-DatoDec3;
2203    for (Int_t j=0; j<fNviews;j++) {        
2204      for (Int_t i=0; i<fNstrips_view;i++) {        DatoDec4=(UShort_t)(dato4*2);
2205              
2206      if((j+1)%2==0) {        DatoDec=DatoDec1*0x0008+DatoDec2*0x0004+DatoDec3*0x0002+DatoDec4*0x0001;
2207      fPedeTrack[j][i]=gRandom->Gaus(fAvePedex,fSigmaPedex);        fDataTrack[fTracklength]=( (Dato << 4) | (DatoDec & 0x000F) );
2208      fSigmaTrack[j][i]=gRandom->Gaus(fAveSigmax,fSigmaSigmax);        CkSum=CkSum^fDataTrack[fTracklength];
2209      };        fTracklength++;
2210      if((j+1)%2==1) {        };
2211      fPedeTrack[j][i]=gRandom->Gaus(fAvePedey,fSigmaPedey);  
2212      fSigmaTrack[j][i]=gRandom->Gaus(fAveSigmay,fSigmaSigmay);        for (Int_t k=0; k<fNstrips_ladder;k++) {
2213      };        // write in buffer the current LADDER
2214              Dato=(UShort_t)fSigmaTrack[j][i*fNstrips_ladder+k];
2215      };        dato1=fSigmaTrack[j][i*fNstrips_ladder+k]-Dato;
2216    };      
2217          DatoDec1=(UShort_t)(dato1*2);
2218            dato2=dato1*2-DatoDec1;
2219      
2220  };        DatoDec2=(UShort_t)(dato2*2);
2221          dato3=dato2*2-DatoDec2;
2222  void Digitizer::LoadMipCor() {        
2223  std:: cout << "Entering LoadMipCor" << endl;        DatoDec3=(UShort_t)(dato3*2);
2224    Float_t xfactor=1./151.6*1.04;        dato4=dato3*2-DatoDec3;
2225    Float_t yfactor=1./152.1;        
2226          DatoDec4=(UShort_t)(dato4*2);
2227    fMipCor[0][0]=140.02*yfactor;        
2228    fMipCor[0][1]=140.99*xfactor;        DatoDec=DatoDec1*0x0008+DatoDec2*0x0004+DatoDec3*0x0002+DatoDec4*0x0001;
2229    fMipCor[0][2]=134.48*yfactor;        
2230    fMipCor[0][3]=144.41*xfactor;        fDataTrack[fTracklength]=( (Dato << 4) | (DatoDec & 0x000F) );
2231    fMipCor[0][4]=140.74*yfactor;        CkSum=CkSum^fDataTrack[fTracklength];
2232    fMipCor[0][5]=142.28*xfactor;        fTracklength++;
2233    fMipCor[0][6]=134.53*yfactor;        };
2234    fMipCor[0][7]=140.63*xfactor;        
2235    fMipCor[0][8]=135.55*yfactor;        for (Int_t k=0; k<64;k++) {
2236    fMipCor[0][9]=138.00*xfactor;        fDataTrack[fTracklength]=0x0000;
2237    fMipCor[0][10]=154.95*yfactor;        CkSum=CkSum^fDataTrack[fTracklength];
2238    fMipCor[0][11]=158.44*xfactor;        fTracklength++;
2239      
2240            };
2241    fMipCor[1][0]=136.07*yfactor;        // end ladder
2242    fMipCor[1][1]=135.59*xfactor;  
2243    fMipCor[1][2]=142.69*yfactor;      // write in buffer the end ladder word
2244    fMipCor[1][3]=138.19*xfactor;      if(i==0) fDataTrack[fTracklength]=0x1807;
2245    fMipCor[1][4]=137.35*yfactor;      if(i==1) fDataTrack[fTracklength]=0x1808;
2246    fMipCor[1][5]=140.23*xfactor;      if(i==2) fDataTrack[fTracklength]=0x1809;
2247    fMipCor[1][6]=153.15*yfactor;      CkSum=CkSum^fDataTrack[fTracklength];
2248    fMipCor[1][7]=151.42*xfactor;      fTracklength++;
2249    fMipCor[1][8]=129.76*yfactor;  
2250    fMipCor[1][9]=140.63*xfactor;      // write in buffer the TRAILER
2251    fMipCor[1][10]=157.87*yfactor;      ReLength=(UShort_t)((fNstrips_ladder*2+64+1)*2+3);
2252    fMipCor[1][11]=153.64*xfactor;      OveCheckCode=0x0000;
2253    
2254    fMipCor[2][0]=134.98*yfactor;      fDataTrack[fTracklength]=0x0000;
2255    fMipCor[2][1]=143.95*xfactor;      fTracklength++;
2256    fMipCor[2][2]=140.23*yfactor;    
2257    fMipCor[2][3]=138.88*xfactor;      fDataTrack[fTracklength]=(ReLength >> 8);
2258    fMipCor[2][4]=137.95*yfactor;      fTracklength++;
2259    fMipCor[2][5]=134.87*xfactor;    
2260    fMipCor[2][6]=157.56*yfactor;      fDataTrack[fTracklength]=( (ReLength << 8) | (OveCheckCode & 0x00FF) );
2261    fMipCor[2][7]=157.31*xfactor;      fTracklength++;
2262    fMipCor[2][8]=141.37*yfactor;  
2263    fMipCor[2][9]=143.39*xfactor;      // end TRAILER        
2264    fMipCor[2][10]=156.15*yfactor;      };
2265    fMipCor[2][11]=158.79*xfactor;  
2266      // write in buffer the DSP header
2267  /*  
2268    for (Int_t j=0; j<fNviews;j++) {    fDataTrack[DSPpos]=(0xE800 | ( ((j+1) << 3) | 0x0005) );
2269      for (Int_t i=0; i<fNstrips_view;i++) {    
2270      fMipCor[j][i]=1.;    fDataTrack[DSPpos+1]=0x01A9;
2271      };  
2272    };        fDataTrack[DSPpos+2]=0x8740;
2273      
2274          EVENT_CAL=0;
2275  */      fDataTrack[DSPpos+3]=(0x1A00 | ( (0x03FF & EVENT_CAL)>> 1) );
2276  };    
2277      PED_L1=0;
2278  void Digitizer::CompressTrackData(Float_t AdcTrack[fNviews][fNstrips_view]) {    fDataTrack[DSPpos+4]=( ((EVENT_CAL << 15) | 0x5002 ) | ((0x03FF & PED_L1) << 2) );
2279  // copy of the corresponding compression fortran routine + new digitization    
2280  // std:: cout << "Entering CompressTrackData " << endl;    // FROM HERE WE WRITE AS ALL VARIABLE apart CkSum are =0  
2281  Int_t oldval=0;  
2282  Int_t newval=0;    fDataTrack[DSPpos+5]=0x8014;
2283  Int_t trasmesso=0;    
2284  Int_t ntrastot=0;    fDataTrack[DSPpos+6]=0x00A0;
2285  Float_t real;    
2286  Float_t inte;    fDataTrack[DSPpos+7]=0x0500;
2287  Int_t cercacluster=0;    
2288  Int_t kt=0;    fDataTrack[DSPpos+8]=0x2801;
2289  static const int DSPbufferSize = 4000; // 13 bit buffer to be rearranged in 16 bit Track buffer    
2290  UShort_t DataDSP[DSPbufferSize];  // 13 bit  buffer to be rearranged in 16 bit Track buffer    fDataTrack[DSPpos+9]=0x400A;
2291  UShort_t DSPlength;  // 13 bit buffer to be rearranged in 16 bit Track buffer    
2292      fDataTrack[DSPpos+10]=0x0050;
2293  memset(fDataTrack,0,sizeof(UShort_t)*fTRACKbuffer); // probably not necessary becouse already done ?    
2294  fTracklength=0;    CkSum=(CkSum >> 8)^(CkSum&0x00FF);
2295      fDataTrack[DSPpos+11]=(0x0280 | (CkSum >> 3));
2296    for (Int_t iv=0; iv<fNviews;iv++) {    
2297    memset(DataDSP,0,sizeof(UShort_t)*DSPbufferSize);    fDataTrack[DSPpos+12]=(0x1FFF | (CkSum << 13) );
2298    DSPlength=16; // skip the header, to be written later  
2299    UShort_t CheckSum=0;    // end dsp header
2300  // write dsp header on buffer  
2301      // write in buffer the TRAILER
2302  //    fDataTrack[fTracklength]=0xE805;    
2303  //    fTracklength++;    ReLength=(UShort_t)((13*2)+3);
2304      OveCheckCode=0x0000;
2305  //    fDataTrack[fTracklength]=0x01A9;    fDataTrack[DSPpos+13]=0x0000;
2306  //    fTracklength++;  
2307      fDataTrack[DSPpos+14]=(ReLength >> 8);
2308  // end dsp header    
2309      fDataTrack[DSPpos+15]=( (ReLength << 8) | (OveCheckCode & 0x00FF) );
2310     //    
2311     // INIZIO VISTA IV - TAKE PROPER ACTION    // end TRAILER
2312     //  
2313    
2314    
2315      
2316      for (Int_t ladder=0; ladder<fNladder;ladder++) {    // end DSP    
2317        Int_t k=0;    };    
2318        while (k<fNstrips_ladder) {  
2319          // compress write in buffer the current LADDER  
2320          if ( k == 0)  {  
2321            real=modff(AdcTrack[iv][ladder*fNstrips_ladder+k],&inte);  };
2322            if (real > 0.5) inte=inte+1;  
2323            newval=(Int_t)inte -(Int_t)fPedeTrack[iv][ladder*fNstrips_ladder+k];  void Digitizer::WriteTrackCalib() {
2324            // first strip of ladder is transmitted  
2325            // DC_TOT first " << AdcTrack[iv][ladder*fNstrips_ladder+k] << endl;  
2326            DataDSP[DSPlength]=( ((UShort_t)inte) & 0x0FFF);  std:: cout << " Entering WriteTrackCalib " << endl;
2327            DSPlength++;    
2328            ntrastot++;  fOutputfile.write(reinterpret_cast<char*>(fDataPSCU),sizeof(UShort_t)*fPSCUbuffer);
2329            trasmesso=1;  
2330            oldval=newval;  UShort_t temp[1000000];
2331            kt=k;  memset(temp,0,sizeof(UShort_t)*1000000);
2332            k++;  swab(fDataTrack,temp,sizeof(UShort_t)*fTracklength);  // WE MUST SWAP THE BYTES!!!
2333            continue;  fOutputfile.write(reinterpret_cast<char*>(temp),sizeof(UShort_t)*fTracklength);
2334          };  fTracklength=0;
2335          real=modff(AdcTrack[iv][ladder*fNstrips_ladder+k],&inte);  if ( fPadding ){
2336          if (real > 0.5) inte=inte+1;        fOutputfile.write(reinterpret_cast<char*>(fDataPadding),sizeof(UChar_t)*fPadding);
2337          newval=(Int_t)inte -(Int_t)(fPedeTrack[iv][ladder*fNstrips_ladder+k]);  };
2338          cercacluster=1; // ?????????  
2339          if (cercacluster==1) {  };
2340            
2341   // controlla l'ordine di tutti queste strip ladder e DSP !!!!!!!        
2342            Int_t diff=0;  void Digitizer::ClearTrackCalib() {
2343    
2344              std:: cout << "Entering ClearTrackCalib " << endl;
2345            switch ((iv+1)%2) {      
2346            case 0: diff=newval-oldval;    
2347            break;  };
2348            case 1: diff=oldval-newval;      
2349            break;  
2350            };  void Digitizer::LoadTrackCalib() {
2351    std:: cout << "Entering LoadTrackCalib " << endl;
2352            if (diff>fCutclu*(Int_t)fSigmaTrack[iv][ladder*fNstrips_ladder+k]) {  
2353              Int_t clval=newval;  // Generate the pedestals and sigmas according to parametrization
2354              Int_t klp=k;        // go on to search for maximum    for (Int_t j=0; j<fNviews;j++) {
2355              klp++;      for (Int_t i=0; i<fNstrips_view;i++) {
2356        
2357              while(klp<fNstrips_ladder) {      if((j+1)%2==0) {
2358                real=modff(AdcTrack[iv][ladder*fNstrips_ladder+klp],&inte);      fPedeTrack[j][i]=gRandom->Gaus(fAvePedex,fSigmaPedex);
2359                if (real > 0.5) inte=inte+1;      fSigmaTrack[j][i]=gRandom->Gaus(fAveSigmax,fSigmaSigmax);
2360                Int_t clvalp=(Int_t)inte -(Int_t)fPedeTrack[iv][ladder*fNstrips_ladder+klp];      };
2361                if((iv+1)%2==0) {      if((j+1)%2==1) {
2362        fPedeTrack[j][i]=gRandom->Gaus(fAvePedey,fSigmaPedey);
2363                  if(clvalp>clval) {      fSigmaTrack[j][i]=gRandom->Gaus(fAveSigmay,fSigmaSigmay);
2364                     clval=clvalp;      };
2365                     k=klp;}      
2366                  else break; // max of cluster found      };
2367      };    
2368                } else {    
2369      
2370                  if(clvalp<clval) {    
2371                     clval=clvalp;  };
2372                     k=klp;}  
2373                  else break; // max of cluster found  void Digitizer::LoadMipCor() {
2374    std:: cout << "Entering LoadMipCor" << endl;
2375                };    Float_t xfactor=1./151.6*1.04;
2376                    Float_t yfactor=1./152.1;
2377                klp++;  
2378              };    fMipCor[0][0]=140.02*yfactor;
2379      fMipCor[0][1]=140.99*xfactor;
2380              Int_t kl1=k-fNclst; // max of cluster (or end of ladder ?)    fMipCor[0][2]=134.48*yfactor;
2381              trasmesso=0;    fMipCor[0][3]=144.41*xfactor;
2382              if(kl1<0)  kl1=0;    fMipCor[0][4]=140.74*yfactor;
2383      fMipCor[0][5]=142.28*xfactor;
2384              if(kt>=kl1) kl1=kt+1;    fMipCor[0][6]=134.53*yfactor;
2385              if( (kt+1)==kl1 ) trasmesso=1;    fMipCor[0][7]=140.63*xfactor;
2386      fMipCor[0][8]=135.55*yfactor;
2387      fMipCor[0][9]=138.00*xfactor;
2388                  fMipCor[0][10]=154.95*yfactor;
2389              Int_t kl2=k+fNclst;    fMipCor[0][11]=158.44*xfactor;
2390              if(kl2>=fNstrips_ladder) kl2=fNstrips_ladder-1;    
2391      
2392              for(Int_t klt=kl1 ; klt<=kl2 ; klt++) {    fMipCor[1][0]=136.07*yfactor;
2393                if(trasmesso==0) {    fMipCor[1][1]=135.59*xfactor;
2394                //  std:: cout << "STRIP " << klt << endl;    fMipCor[1][2]=142.69*yfactor;
2395                //  std:: cout << "ADC_TOT " <<AdcTrack[iv][ladder*fNstrips_ladder+klt] << endl;    fMipCor[1][3]=138.19*xfactor;
2396      fMipCor[1][4]=137.35*yfactor;
2397                  DataDSP[DSPlength]=( ((UShort_t)klt) | 0x1000);    fMipCor[1][5]=140.23*xfactor;
2398                  DSPlength++;      fMipCor[1][6]=153.15*yfactor;
2399                  ntrastot++;    fMipCor[1][7]=151.42*xfactor;
2400                  fMipCor[1][8]=129.76*yfactor;
2401      fMipCor[1][9]=140.63*xfactor;
2402                  real=modff(AdcTrack[iv][ladder*fNstrips_ladder+klt],&inte);    fMipCor[1][10]=157.87*yfactor;
2403                  if (real > 0.5) inte=inte+1;    fMipCor[1][11]=153.64*xfactor;
2404                  DataDSP[DSPlength]=( ((UShort_t)inte) & 0x0FFF);  
2405                  DSPlength++;    fMipCor[2][0]=134.98*yfactor;
2406                  ntrastot++;    fMipCor[2][1]=143.95*xfactor;
2407                  fMipCor[2][2]=140.23*yfactor;
2408                 }    fMipCor[2][3]=138.88*xfactor;
2409                 else {    fMipCor[2][4]=137.95*yfactor;
2410                 //   std:: cout << "ADC_TOT " <<AdcTrack[iv][ladder*fNstrips_ladder+klt] << endl;    fMipCor[2][5]=134.87*xfactor;
2411                  real=modff(AdcTrack[iv][ladder*fNstrips_ladder+klt],&inte);    fMipCor[2][6]=157.56*yfactor;
2412                  if (real > 0.5) inte=inte+1;    fMipCor[2][7]=157.31*xfactor;
2413                  DataDSP[DSPlength]=( ((UShort_t)inte) & 0x0FFF);    fMipCor[2][8]=141.37*yfactor;
2414                  DSPlength++;                  fMipCor[2][9]=143.39*xfactor;
2415                  ntrastot++;    fMipCor[2][10]=156.15*yfactor;
2416                  };    fMipCor[2][11]=158.79*xfactor;
2417                  trasmesso=1;                          
2418              };  // end trasmission  /*
2419              kt=kl2;    for (Int_t j=0; j<fNviews;j++) {
2420              k=kl2;      for (Int_t i=0; i<fNstrips_view;i++) {
2421              real=modff(AdcTrack[iv][ladder*fNstrips_ladder+kt],&inte);      fMipCor[j][i]=1.;
2422              if (real > 0.5) inte=inte+1;      };
2423              oldval=(Int_t)inte -(Int_t)fPedeTrack[iv][ladder*fNstrips_ladder+kt];    };    
2424              k++;  
2425              continue;      
2426    */  
2427    };
2428            }; // end cercacluster  
2429          }; // end cercacluster  void Digitizer::CompressTrackData(Float_t AdcTrack[fNviews][fNstrips_view]) {
2430          // copy of the corresponding compression fortran routine + new digitization
2431  // start ZOP check for strips no  // std:: cout << "Entering CompressTrackData " << endl;
2432          Int_t oldval=0;
2433        if(abs(newval-oldval)>=fCutzop*(Int_t)fSigmaTrack[iv][ladder*fNstrips_ladder+k]) {  Int_t newval=0;
2434    Int_t trasmesso=0;
2435         if(trasmesso==0) {  Int_t ntrastot=0;
2436         // std:: cout << "STRIP " << k << endl;  Float_t real;
2437         // std:: cout << "ADC_TOT " << AdcTrack[iv][ladder*fNstrips_ladder+k] << endl;  Float_t inte;
2438    Int_t cercacluster=0;
2439           DataDSP[DSPlength]=( ((UShort_t)k) | 0x1000);  Int_t kt=0;
2440           DSPlength++;    static const int DSPbufferSize = 4000; // 13 bit buffer to be rearranged in 16 bit Track buffer
2441           ntrastot++;  UShort_t DataDSP[DSPbufferSize];  // 13 bit  buffer to be rearranged in 16 bit Track buffer
2442                UShort_t DSPlength;  // 13 bit buffer to be rearranged in 16 bit Track buffer
2443    
2444           real=modff(AdcTrack[iv][ladder*fNstrips_ladder+k],&inte);  memset(fDataTrack,0,sizeof(UShort_t)*fTRACKbuffer); // probably not necessary becouse already done ?
2445           if (real > 0.5) inte=inte+1;  fTracklength=0;
2446           DataDSP[DSPlength]=( ((UShort_t)inte) & 0x0FFF);  
2447           DSPlength++;    for (Int_t iv=0; iv<fNviews;iv++) {
2448           ntrastot++;    memset(DataDSP,0,sizeof(UShort_t)*DSPbufferSize);
2449      DSPlength=16; // skip the header, to be written later
2450         }    UShort_t CheckSum=0;
2451         else {  // write dsp header on buffer
2452         //  std:: cout << "ADC_TOT " << AdcTrack[iv][ladder*fNstrips_ladder+k] << endl;  
2453           real=modff(AdcTrack[iv][ladder*fNstrips_ladder+k],&inte);  //    fDataTrack[fTracklength]=0xE805;
2454           if (real > 0.5) inte=inte+1;  //    fTracklength++;
2455           DataDSP[DSPlength]=(  ((UShort_t)inte) & 0x0FFF);  
2456           DSPlength++;  //    fDataTrack[fTracklength]=0x01A9;
2457           ntrastot++;        //    fTracklength++;
2458         };  
2459         trasmesso=1;  // end dsp header
2460         oldval=newval;  
2461         kt=k;     //
2462       // INIZIO VISTA IV - TAKE PROPER ACTION
2463        }       //
2464        else trasmesso=0;  
2465        // end zop  
2466          
2467        k++;            for (Int_t ladder=0; ladder<fNladder;ladder++) {
2468        };  // end cycle inside ladder        Int_t k=0;
2469  // write here the end ladder bytes        while (k<fNstrips_ladder) {
2470  //            std:: cout << "FINE LADDER " << ladder+1 << endl;          // compress write in buffer the current LADDER
2471            if ( k == 0)  {
2472        DataDSP[DSPlength]=( ((UShort_t)(ladder+1))  | 0x1800);            real=modff(AdcTrack[iv][ladder*fNstrips_ladder+k],&inte);
2473        DSPlength++;            if (real > 0.5) inte=inte+1;
2474        ntrastot++;            newval=(Int_t)inte -(Int_t)fPedeTrack[iv][ladder*fNstrips_ladder+k];
2475        trasmesso=0;            // first strip of ladder is transmitted
2476              // DC_TOT first " << AdcTrack[iv][ladder*fNstrips_ladder+k] << endl;
2477      };  //end cycle inside dsp            DataDSP[DSPlength]=( ((UShort_t)inte) & 0x0FFF);
2478  //  std:: cout << "FINE DSP " << iv+1 << endl;            DSPlength++;  
2479  // here put DSP header            ntrastot++;
2480      DataDSP[0]=(0x1CA0 | ((UShort_t)(iv+1)) );            trasmesso=1;
2481      UShort_t Nword=(DSPlength*13)/16;            oldval=newval;
2482      if( ((DSPlength*13)%16)!=0) Nword++;            kt=k;
2483      DataDSP[1]=(0x1400 | ( Nword >> 10));            k++;
2484      DataDSP[2]=(0x1400 | ( Nword & 0x03FF) );            continue;
2485      DataDSP[3]=(0x1400 | (( (UShort_t)(fCounter >> 10) ) & 0x03FF) );          };
2486      DataDSP[4]=(0x1400 | (( (UShort_t)(fCounter) )  & 0x03FF) );          real=modff(AdcTrack[iv][ladder*fNstrips_ladder+k],&inte);
2487      DataDSP[5]=(0x1400 | ( (UShort_t)(fNclst << 7) ) | ( (UShort_t)(fCutzop << 4) )          if (real > 0.5) inte=inte+1;
2488       | ( (UShort_t)fCutzop  ) );          newval=(Int_t)inte -(Int_t)(fPedeTrack[iv][ladder*fNstrips_ladder+k]);
2489      DataDSP[6]=0x1400;          cercacluster=1; // ?????????
2490      DataDSP[7]=0x1400;          if (cercacluster==1) {
2491      DataDSP[8]=0x1400;          
2492      DataDSP[9]=0x1400;   // controlla l'ordine di tutti queste strip ladder e DSP !!!!!!!      
2493      DataDSP[10]=0x1400;            Int_t diff=0;
2494      DataDSP[11]=0x1400;  
2495      DataDSP[12]=0x1400;            
2496      DataDSP[13]=0x1400;            switch ((iv+1)%2) {
2497      DataDSP[14]=(0x1400 | (CheckSum & 0x00FF) );            case 0: diff=newval-oldval;
2498      DataDSP[15]=0x1C00;            break;
2499  // end DSP header                case 1: diff=oldval-newval;    
2500              break;
2501              };
2502  // write 13 bit DataDSP bufer inside 16 bit fDataTrack buffer  
2503      Int_t Bit16free=16;            if (diff>fCutclu*(Int_t)fSigmaTrack[iv][ladder*fNstrips_ladder+k]) {
2504      UShort_t Dato;              Int_t clval=newval;
2505      for (Int_t NDSP=0; NDSP<DSPlength;NDSP++) {              Int_t klp=k;        // go on to search for maximum
2506        Int_t Bit13ToWrite=13;              klp++;
2507        while(Bit13ToWrite>0) {  
2508          if(Bit13ToWrite<=Bit16free) {              while(klp<fNstrips_ladder) {
2509            Dato=((DataDSP[NDSP]&(0xFFFF >> (16-Bit13ToWrite)))<<(Bit16free-Bit13ToWrite));                real=modff(AdcTrack[iv][ladder*fNstrips_ladder+klp],&inte);
2510            fDataTrack[fTracklength]=fDataTrack[fTracklength] | Dato ;                if (real > 0.5) inte=inte+1;
2511            Bit16free=Bit16free-Bit13ToWrite;                Int_t clvalp=(Int_t)inte -(Int_t)fPedeTrack[iv][ladder*fNstrips_ladder+klp];
2512            Bit13ToWrite=0;                if((iv+1)%2==0) {
2513            if(Bit16free==0) {  
2514              if(NDSP>15) CheckSum=CheckSum^fDataTrack[fTracklength];                  if(clvalp>clval) {
2515              fTracklength++;                     clval=clvalp;
2516              Bit16free=16;                     k=klp;}
2517            };                            else break; // max of cluster found
2518          }  
2519          else if(Bit13ToWrite>Bit16free) {                } else {  
2520            Dato=( (DataDSP[NDSP]&(0xFFFF >> (16-Bit13ToWrite) ) ) >> (Bit13ToWrite-Bit16free) );  
2521            fDataTrack[fTracklength]=fDataTrack[fTracklength] | Dato ;                  if(clvalp<clval) {
2522            if(NDSP>15) CheckSum=CheckSum^fDataTrack[fTracklength];                     clval=clvalp;
2523            fTracklength++;                     k=klp;}
2524            Bit13ToWrite=Bit13ToWrite-Bit16free;                  else break; // max of cluster found
2525            Bit16free=16;    
2526          };                };
2527                          
2528        }; // end cycle while(Bit13ToWrite>0)                klp++;
2529                          };
2530      }; // end cycle DataDSP  
2531      if(Bit16free!=16) { fTracklength++; CheckSum=CheckSum^fDataTrack[fTracklength]; };              Int_t kl1=k-fNclst; // max of cluster (or end of ladder ?)
2532      CheckSum=(CheckSum >> 8)^(CheckSum&0x00FF);              trasmesso=0;
2533      fDataTrack[fTracklength-Nword+11]=(0x0280 | (CheckSum >> 3));              if(kl1<0)  kl1=0;
2534      fDataTrack[fTracklength-Nword+12]=(0x1C00 | (CheckSum << 13) );  
2535                if(kt>=kl1) kl1=kt+1;
2536  // end write 13 bit DataDSP bufer inside 16 bit fDataTrack buffer              if( (kt+1)==kl1 ) trasmesso=1;
2537    
2538  //write trailer on buffer  
2539      UShort_t ReLength=(UShort_t)((Nword+13)*2+3);              
2540      UShort_t OveCheckCode=0x0000;              Int_t kl2=k+fNclst;
2541                if(kl2>=fNstrips_ladder) kl2=fNstrips_ladder-1;
2542      fDataTrack[fTracklength]=0x0000;  
2543      fTracklength++;              for(Int_t klt=kl1 ; klt<=kl2 ; klt++) {
2544                    if(trasmesso==0) {
2545      fDataTrack[fTracklength]=(ReLength >> 8);                //  std:: cout << "STRIP " << klt << endl;
2546      fTracklength++;                //  std:: cout << "ADC_TOT " <<AdcTrack[iv][ladder*fNstrips_ladder+klt] << endl;
2547      
2548      fDataTrack[fTracklength]=( (ReLength << 8) | (OveCheckCode & 0x00FF) );                  DataDSP[DSPlength]=( ((UShort_t)klt) | 0x1000);
2549      fTracklength++;                    DSPlength++;  
2550  // end trailer                  ntrastot++;
2551  //    std:: cout  << "DSPlength  " <<DSPlength << endl;              
2552  //    std:: cout << "Nword " << Nword  << endl;  
2553  //    std:: cout <<  "ReLength " << ReLength << endl;                  real=modff(AdcTrack[iv][ladder*fNstrips_ladder+klt],&inte);
2554    };                      if (real > 0.5) inte=inte+1;
2555  //    std:: cout << "ntrastot " << ntrastot << endl;                      DataDSP[DSPlength]=( ((UShort_t)inte) & 0x0FFF);
2556                    DSPlength++;
2557  };                  ntrastot++;
2558                
2559                   }
2560  Float_t Digitizer::SaturationTrack(Float_t ADC) {                 else {
2561    Float_t SatFact=1.;                 //   std:: cout << "ADC_TOT " <<AdcTrack[iv][ladder*fNstrips_ladder+klt] << endl;
2562    if(ADC<70.) { SatFact=80./ADC; };                  real=modff(AdcTrack[iv][ladder*fNstrips_ladder+klt],&inte);
2563    if(ADC>3000.) { SatFact=3000./ADC; };                  if (real > 0.5) inte=inte+1;
2564    return SatFact;                  DataDSP[DSPlength]=( ((UShort_t)inte) & 0x0FFF);
2565  };                  DSPlength++;              
2566                    ntrastot++;
2567                    };
2568                    trasmesso=1;                        
2569                };  // end trasmission
2570                kt=kl2;
2571                k=kl2;
2572                real=modff(AdcTrack[iv][ladder*fNstrips_ladder+kt],&inte);
2573                if (real > 0.5) inte=inte+1;
2574                oldval=(Int_t)inte -(Int_t)fPedeTrack[iv][ladder*fNstrips_ladder+kt];
2575                k++;
2576                continue;
2577    
2578    
2579              }; // end cercacluster
2580            }; // end cercacluster
2581          
2582    // start ZOP check for strips no
2583          
2584          if(abs(newval-oldval)>=fCutzop*(Int_t)fSigmaTrack[iv][ladder*fNstrips_ladder+k]) {
2585    
2586           if(trasmesso==0) {
2587           // std:: cout << "STRIP " << k << endl;
2588           // std:: cout << "ADC_TOT " << AdcTrack[iv][ladder*fNstrips_ladder+k] << endl;
2589    
2590             DataDSP[DSPlength]=( ((UShort_t)k) | 0x1000);
2591             DSPlength++;  
2592             ntrastot++;
2593                
2594    
2595             real=modff(AdcTrack[iv][ladder*fNstrips_ladder+k],&inte);
2596             if (real > 0.5) inte=inte+1;
2597             DataDSP[DSPlength]=( ((UShort_t)inte) & 0x0FFF);
2598             DSPlength++;
2599             ntrastot++;
2600    
2601           }
2602           else {
2603           //  std:: cout << "ADC_TOT " << AdcTrack[iv][ladder*fNstrips_ladder+k] << endl;
2604             real=modff(AdcTrack[iv][ladder*fNstrips_ladder+k],&inte);
2605             if (real > 0.5) inte=inte+1;
2606             DataDSP[DSPlength]=(  ((UShort_t)inte) & 0x0FFF);
2607             DSPlength++;
2608             ntrastot++;      
2609           };
2610           trasmesso=1;
2611           oldval=newval;
2612           kt=k;
2613    
2614          }  
2615          else trasmesso=0;
2616          // end zop
2617          
2618          k++;      
2619          };  // end cycle inside ladder
2620    // write here the end ladder bytes
2621    //            std:: cout << "FINE LADDER " << ladder+1 << endl;
2622    
2623          DataDSP[DSPlength]=( ((UShort_t)(ladder+1))  | 0x1800);
2624          DSPlength++;
2625          ntrastot++;
2626          trasmesso=0;
2627    
2628        };  //end cycle inside dsp
2629    //  std:: cout << "FINE DSP " << iv+1 << endl;
2630    // here put DSP header
2631        DataDSP[0]=(0x1CA0 | ((UShort_t)(iv+1)) );
2632        UShort_t Nword=(DSPlength*13)/16;
2633        if( ((DSPlength*13)%16)!=0) Nword++;
2634        DataDSP[1]=(0x1400 | ( Nword >> 10));
2635        DataDSP[2]=(0x1400 | ( Nword & 0x03FF) );
2636        DataDSP[3]=(0x1400 | (( (UShort_t)(fCounter >> 10) ) & 0x03FF) );
2637        DataDSP[4]=(0x1400 | (( (UShort_t)(fCounter) )  & 0x03FF) );
2638        DataDSP[5]=(0x1400 | ( (UShort_t)(fNclst << 7) ) | ( (UShort_t)(fCutzop << 4) )
2639         | ( (UShort_t)fCutzop  ) );
2640        DataDSP[6]=0x1400;
2641        DataDSP[7]=0x1400;
2642        DataDSP[8]=0x1400;
2643        DataDSP[9]=0x1400;
2644        DataDSP[10]=0x1400;
2645        DataDSP[11]=0x1400;
2646        DataDSP[12]=0x1400;
2647        DataDSP[13]=0x1400;
2648        DataDSP[14]=(0x1400 | (CheckSum & 0x00FF) );
2649        DataDSP[15]=0x1C00;
2650    // end DSP header    
2651    
2652    
2653    // write 13 bit DataDSP bufer inside 16 bit fDataTrack buffer
2654        Int_t Bit16free=16;
2655        UShort_t Dato;
2656        for (Int_t NDSP=0; NDSP<DSPlength;NDSP++) {
2657          Int_t Bit13ToWrite=13;
2658          while(Bit13ToWrite>0) {
2659            if(Bit13ToWrite<=Bit16free) {
2660              Dato=((DataDSP[NDSP]&(0xFFFF >> (16-Bit13ToWrite)))<<(Bit16free-Bit13ToWrite));
2661              fDataTrack[fTracklength]=fDataTrack[fTracklength] | Dato ;
2662              Bit16free=Bit16free-Bit13ToWrite;
2663              Bit13ToWrite=0;
2664              if(Bit16free==0) {
2665                if(NDSP>15) CheckSum=CheckSum^fDataTrack[fTracklength];
2666                fTracklength++;
2667                Bit16free=16;
2668              };          
2669            }
2670            else if(Bit13ToWrite>Bit16free) {
2671              Dato=( (DataDSP[NDSP]&(0xFFFF >> (16-Bit13ToWrite) ) ) >> (Bit13ToWrite-Bit16free) );
2672              fDataTrack[fTracklength]=fDataTrack[fTracklength] | Dato ;
2673              if(NDSP>15) CheckSum=CheckSum^fDataTrack[fTracklength];
2674              fTracklength++;
2675              Bit13ToWrite=Bit13ToWrite-Bit16free;
2676              Bit16free=16;  
2677            };
2678            
2679          }; // end cycle while(Bit13ToWrite>0)
2680              
2681        }; // end cycle DataDSP
2682        if(Bit16free!=16) { fTracklength++; CheckSum=CheckSum^fDataTrack[fTracklength]; };
2683        CheckSum=(CheckSum >> 8)^(CheckSum&0x00FF);
2684        fDataTrack[fTracklength-Nword+11]=(0x0280 | (CheckSum >> 3));
2685        fDataTrack[fTracklength-Nword+12]=(0x1C00 | (CheckSum << 13) );
2686    
2687    // end write 13 bit DataDSP bufer inside 16 bit fDataTrack buffer
2688    
2689    //write trailer on buffer
2690        UShort_t ReLength=(UShort_t)((Nword+13)*2+3);
2691        UShort_t OveCheckCode=0x0000;
2692    
2693        fDataTrack[fTracklength]=0x0000;
2694        fTracklength++;
2695      
2696        fDataTrack[fTracklength]=(ReLength >> 8);
2697        fTracklength++;
2698      
2699        fDataTrack[fTracklength]=( (ReLength << 8) | (OveCheckCode & 0x00FF) );
2700        fTracklength++;  
2701    // end trailer
2702    //    std:: cout  << "DSPlength  " <<DSPlength << endl;
2703    //    std:: cout << "Nword " << Nword  << endl;
2704    //    std:: cout <<  "ReLength " << ReLength << endl;
2705      };    
2706    //    std:: cout << "ntrastot " << ntrastot << endl;    
2707    
2708    };
2709    
2710    
2711    Float_t Digitizer::SaturationTrack(Float_t ADC) {
2712      Float_t SatFact=1.;
2713      if(ADC<70.) { SatFact=80./ADC; };
2714      if(ADC>3000.) { SatFact=3000./ADC; };
2715      return SatFact;
2716    };
2717    
2718    
2719    
2720    
2721    
2722    

Legend:
Removed from v.1.3  
changed lines
  Added in v.1.5

  ViewVC Help
Powered by ViewVC 1.1.23