9 #include "AnitaEventCalibrator.h" 10 #include "UsefulAnitaEvent.h" 11 #include "AnitaVersion.h" 20 static const char * voltageCalibFiles[] = { 0, 0, 0,
"simpleVoltageCalibrationHarm.txt",
"simpleVoltageCalibrationAnita4.txt" };
21 static const char * relativeCableDelayFiles[] = { 0,0,0,
"relativeCableDelays.dat",
"relativeCableDelaysAnita4.dat"};
22 static const char * relativePhaseCenterToAmpaDelaysFiles[] = { 0,0,0,
"relativePhaseCenterToAmpaDelays.dat",
"relativePhaseCenterToAmpaDelaysAnita4.dat"};
32 firstHitBusRcoLatchLimit = 40;
38 for(
int surf=0; surf < NUM_SURF; surf++){
40 for(
int samp=0; samp < NUM_SAMP; samp++){
44 for(
int chan=0; chan < NUM_CHAN; chan++){
45 for(
int samp=0; samp < NUM_SAMP; samp++){
57 AnitaEventCalibrator::~AnitaEventCalibrator(){
60 deleteClockAlignmentTGraphs();
64 static TMutex instance_lock;
70 if (!v) v = AnitaVersion::get();
73 __asm__ __volatile__ (
"" :::
"memory");
82 __asm__ __volatile__ (
"" :::
"memory");
85 instance_lock.UnLock();
96 for(Int_t surf=0; surf<NUM_SURF; surf++){
97 clockAlignment.push_back(0);
99 grClocks.push_back(NULL);
101 grCorClock.push_back(NULL);
105 measuredClockPeriods.push_back(std::vector<std::vector<Double_t> > (NUM_RCO, std::vector<Double_t>(AnitaClock::maxNumZcs, 0)));
108 const Int_t bufferSize = 300;
143 Bool_t fUnwrap =
false;
144 Bool_t fBinToBinDts =
false;
145 Bool_t fNominal =
false;
146 Bool_t fApplyTempCorrection =
true;
147 Bool_t fVoltage =
false;
148 Bool_t fApplyTriggerJitterCorrection =
false;
149 Bool_t fApplyCableDelays =
false;
150 Bool_t fZeroMeanNonClockChannels =
false;
151 Bool_t fFlipRcoPhase =
false;
152 Bool_t fFirmwareRcoNoLatch =
false;
153 Bool_t fAddPedestal =
false;
154 Bool_t fApplyExtraDelayFromPhaseCenter =
false;
155 Bool_t fRemoveClockSpike =
false;
158 case WaveCalType::kJustRemoveClockSpike:
159 fRemoveClockSpike =
true;
163 std::cerr <<
"Warning in " << __PRETTY_FUNCTION__ <<
", calling kNotACalib will be treated as kNoCalib" 167 fApplyTempCorrection =
false;
171 fRemoveClockSpike =
true;
173 fApplyTempCorrection =
true;
178 fRemoveClockSpike =
true;
180 fApplyTempCorrection =
true;
188 fRemoveClockSpike =
true;
192 fApplyTempCorrection =
true;
196 fRemoveClockSpike =
true;
200 fFlipRcoPhase =
true;
204 fRemoveClockSpike =
true;
208 fApplyTempCorrection =
true;
209 fFirmwareRcoNoLatch =
true;
213 fRemoveClockSpike =
true;
217 fFirmwareRcoNoLatch =
true;
218 fFlipRcoPhase =
true;
222 fRemoveClockSpike =
true;
225 fApplyTempCorrection =
true;
227 fApplyTriggerJitterCorrection =
true;
228 fApplyCableDelays =
false;
229 fZeroMeanNonClockChannels =
true;
239 fRemoveClockSpike =
true;
242 fApplyTempCorrection =
true;
243 fApplyTriggerJitterCorrection =
true;
244 fApplyCableDelays =
true;
245 fZeroMeanNonClockChannels =
true;
246 fApplyExtraDelayFromPhaseCenter =
true;
252 fZeroMeanNonClockChannels =
true;
256 fRemoveClockSpike =
true;
259 fApplyTempCorrection =
true;
261 fApplyTriggerJitterCorrection =
true;
262 fApplyCableDelays =
true;
263 fZeroMeanNonClockChannels =
true;
264 fApplyExtraDelayFromPhaseCenter =
true;
268 fRemoveClockSpike =
true;
271 fApplyTempCorrection =
false;
273 fApplyTriggerJitterCorrection=
false;
274 fApplyCableDelays=
true;
275 fZeroMeanNonClockChannels=
true;
276 fApplyExtraDelayFromPhaseCenter=
true;
287 if(fRemoveClockSpike==
true){
289 for(Int_t samp=0;samp<NUM_SAMP;samp++){
290 if((eventPtr->
chipIdFlag[9*NUM_CHAN + 8]&0x03) == 0x01 and eventPtr->
data[9*NUM_CHAN + 8][samp] >300 ){
291 eventPtr->
data[9*NUM_CHAN + 8][samp] -= 512;
296 for(Int_t surf=0; surf<NUM_SURF; surf++){
299 for(Int_t samp=0;samp<NUM_SAMP;samp++){
300 if(eventPtr->
data[surf*NUM_CHAN + 8][samp] <-200 or eventPtr->
data[surf*NUM_CHAN + 8][samp] > 200){
306 for(Int_t chan=0;chan<NUM_CHAN-1;chan++){
307 for(Int_t samp=0;samp<NUM_SAMP;samp++){
309 if(surf == 9 and (eventPtr->
chipIdFlag[surf*NUM_CHAN + chan]&0x03) == 0x01 and eventPtr->
data[surf*NUM_CHAN + chan][samp]>358 and eventPtr->
data[surf*NUM_CHAN + chan][samp]<470){
310 eventPtr->
data[surf*NUM_CHAN + chan][samp] -= 512;
312 if(eventPtr->
data[surf*NUM_CHAN + chan][samp]< -470 or eventPtr->
data[surf*NUM_CHAN + chan][samp]>470){
314 eventPtr->SpikeyRFChannelList.push_back(surf*NUM_CHAN + chan);
332 if(fBinToBinDts==
true){
340 for(Int_t surf=0; surf<NUM_SURF; surf++){
347 if(fFirmwareRcoNoLatch==
true){
348 for(Int_t surf=0; surf<NUM_SURF; surf++){
353 if(fFlipRcoPhase==
true){
354 for(Int_t surf=0; surf<NUM_SURF; surf++){
360 for(Int_t surf=0; surf<NUM_SURF; surf++){
382 for(Int_t surf=0; surf<NUM_SURF; surf++){
387 for(Int_t surf=0; surf<NUM_SURF; surf++){
398 for(Int_t surf = 0; surf < NUM_SURF; surf++){
399 for(Int_t chan = 0; chan < NUM_CHAN; chan++){
401 rcoVector.at(surf), fApplyTempCorrection, fAddPedestal,
406 else if(fUnwrap==
false){
408 for(Int_t surf = 0; surf < NUM_SURF; surf++){
411 Int_t clockIndex = surf*NUM_CHAN + 8;
412 Int_t labChip = eventPtr->
getLabChip(clockIndex);
414 if(rco < 0 || rco > 1){
415 std::cerr <<
"Error in rco array!" << __FILE__ <<
": " << __LINE__ << std::endl;
423 Int_t needToFlipRco = latestSample<earliestSample ? 1 : 0;
427 if(samp==earliestSample && needToFlipRco){
433 for(Int_t chan = 0; chan < NUM_CHAN; chan++){
434 Int_t chanIndex = surf*NUM_CHAN + chan;
437 if(fAddPedestal==
true){
451 if(fBinToBinDts==
false){
453 for(Int_t surf = 0; surf < NUM_SURF; surf++){
471 applyVoltageCalibration(eventPtr);
487 if(fApplyTriggerJitterCorrection==
true){
492 for(Int_t surf=0; surf<NUM_SURF; surf++){
498 for(Int_t surf=0; surf<NUM_SURF; surf++){
504 for(Int_t surf=0; surf<NUM_SURF; surf++){
507 timeArray[surf][samp] -= clockAlignment.at(surf);
523 if(fZeroMeanNonClockChannels==
true){
524 zeroMeanNonClockChannels();
537 for(Int_t surf=0; surf<NUM_SURF; surf++){
540 for(Int_t chan=0; chan<NUM_CHAN; chan++){
541 Int_t chanIndex = surf*CHANNELS_PER_SURF + chan;
545 Double_t cableDelay = 0;
546 if(fApplyCableDelays==
true){
547 Int_t labChip = eventPtr->
getLabChip(chanIndex);
550 if(fApplyExtraDelayFromPhaseCenter==
true){
557 eventPtr->
fTimes[chanIndex][samp] =
timeArray[surf][samp] + cableDelay;
576 void AnitaEventCalibrator::applyVoltageCalibration(
UsefulAnitaEvent* eventPtr){
578 for(Int_t surf=0; surf<NUM_SURF; surf++){
579 for(Int_t chan=0; chan<RFCHAN_PER_SURF; chan++){
580 Int_t chanIndex = surf*NUM_CHAN + chan;
581 Int_t labChip = eventPtr->
getLabChip(chanIndex);
597 void AnitaEventCalibrator::zeroMeanNonClockChannels(){
598 for(Int_t surf=0; surf<NUM_SURF; surf++){
599 for(Int_t chan=0; chan<RFCHAN_PER_SURF; chan++){
609 std::vector<Double_t> AnitaEventCalibrator::getClockAlignment(
UsefulAnitaEvent* eventPtr,
610 Int_t numPoints[NUM_SURF],
611 Double_t volts[NUM_SURF][NUM_CHAN][NUM_SAMP],
612 Double_t times[NUM_SURF][NUM_SAMP]){
619 void AnitaEventCalibrator::deleteClockAlignmentTGraphs(){
622 for(Int_t surf=0; surf<NUM_SURF; surf++){
624 clockAlignment.at(surf) = 0;
625 if(grClocks.at(surf)) {
626 delete grClocks.at(surf);
627 grClocks.at(surf) = NULL;
633 if(grCorClock.at(surf)){
634 delete grCorClock.at(surf);
635 grCorClock.at(surf) = NULL;
640 for(std::map<Double_t, TGraph*>::iterator itr =
grClock0s.begin(); itr !=
grClock0s.end(); ++itr){
653 std::vector<Double_t> AnitaEventCalibrator::getClockAlignment(
UsefulAnitaEvent* eventPtr,
654 Int_t numPoints[NUM_SURF],
655 Double_t volts[NUM_SURF][NUM_CHAN][NUM_SAMP],
656 Double_t times[NUM_SURF][NUM_SAMP],
657 std::vector<Int_t> listOfClockNums){
668 deleteClockAlignmentTGraphs();
675 const Int_t minNumPointsToTryInterpolation = 10;
676 for(UInt_t surfInd=0; surfInd<listOfClockNums.size(); surfInd++){
680 if(numPoints[surfInd] <= minNumPointsToTryInterpolation){
685 std::vector<Double_t> zeroClockOffsets(NUM_SURF, 0);
686 return zeroClockOffsets;
694 for(UInt_t surfInd=0; surfInd<listOfClockNums.size(); surfInd++){
695 Int_t surf = listOfClockNums.at(surfInd);
704 grClocks.at(surf) =
new TGraph(numPoints[surf], times[surf], volts[surf][8]);
707 Int_t lab = eventPtr->
getLabChip(surfInd*NUM_CHAN + 8);
710 TGraph* grClock0 = NULL;
713 TGraph* grTemp0 =
new TGraph(numPoints[0], times[0], volts[0][8]);
722 keepOnlySomeTimeAfterClockUptick(grClock0, deltaClockKeepNs);
725 grClock0 =
grClock0s.find(deltaClockKeepNs)->second;
727 keepOnlySomeTimeAfterClockUptick(
grClockInterps.at(surf), deltaClockKeepNs);
733 Double_t maxVal = -1001;
734 Double_t clockAlignmentTemp = 0;
735 for(Int_t samp=0; samp<grCorClock.at(surf)->GetN(); samp++){
736 if(TMath::Abs(grCorClock.at(surf)->GetX()[samp]) <= AnitaClock::meanPeriodNs/2){
737 if(grCorClock.at(surf)->GetY()[samp] > maxVal){
738 maxVal = grCorClock.at(surf)->GetY()[samp];
739 clockAlignmentTemp = grCorClock.at(surf)->GetX()[samp];
744 clockAlignment.at(surf) = clockAlignmentTemp;
747 for(Int_t samp=0; samp <
grClockInterps.at(surf)->GetN(); samp++){
750 for(Int_t samp=0; samp < grClocks.at(surf)->GetN(); samp++){
751 grClocks.at(surf)->GetX()[samp] -= clockAlignment.at(surf);
768 std::cerr <<
"FFTtools currently disabled." << std::endl;
771 return clockAlignment;
780 void AnitaEventCalibrator::keepOnlySomeTimeAfterClockUptick(TGraph* grClock, Double_t deltaClockKeepNs){
783 if(deltaClockKeepNs > 0){
788 std::vector<Double_t> timeZeroCrossings(AnitaClock::maxNumZcs, 0);
789 std::vector<Int_t> sampZeroCrossings(AnitaClock::maxNumZcs, 0);
791 Int_t numZc = getTimeOfUpwardsClockTicksCrossingZero(grClock->GetN(),
801 for(Int_t samp=0; samp<grClock->GetN(); samp++){
803 if(grClock->GetX()[samp] - timeZeroCrossings[thisZc] < deltaClockKeepNs &&
804 grClock->GetX()[samp] - timeZeroCrossings[thisZc] >= 0){
807 grClock->GetY()[samp] = 0;
810 if(timeZeroCrossings[thisZc] < grClock->GetX()[samp] - deltaClockKeepNs){
811 if(thisZc < numZc-1){
829 for(Int_t surf=0; surf<NUM_SURF; surf++){
830 Int_t lab = eventPtr->
getLabChip(surf*NUM_CHAN+8);
833 Double_t tempFactor = 1;
834 if(oldMeanClockPeriod > 1e-6){
835 tempFactor = AnitaClock::meanPeriodNs/oldMeanClockPeriod;
854 for(Int_t surf=0; surf<NUM_SURF; surf++){
857 Double_t meanClockDt = 0;
860 for(Int_t zc=0; zc<AnitaClock::maxNumZcs; zc++){
861 if(measuredClockPeriods.at(surf).at(rco).at(zc) > 0){
862 meanClockDt += measuredClockPeriods.at(surf).at(rco).at(zc)/currentTempFactor;
867 meanClockDt /= count;
868 Int_t lab = eventPtr->
getLabChip(surf*NUM_CHAN + 8);
888 Double_t clockVolts[NUM_SURF][NUM_RCO][NUM_SAMP] = {{{0}}};
889 Double_t clockTimes[NUM_SURF][NUM_RCO][NUM_SAMP] = {{{0}}};
890 Int_t clockCapacitorNums[NUM_SURF][NUM_RCO][NUM_SAMP] = {{{0}}};
891 Int_t clockNumPoints[NUM_SURF][NUM_RCO] = {{0}};
894 for(Int_t surf=0; surf<NUM_SURF; surf++){
895 for(Int_t rco=0; rco<NUM_RCO; rco++){
896 clockNumPoints[surf][rco] =
unwrapChannel(eventPtr, surf, 8, rco,
true,
false,
897 clockVolts[surf][rco], clockTimes[surf][rco],
898 clockCapacitorNums[surf][rco]);
923 std::vector<std::vector<std::vector<Double_t> > > timeZeroCrossings(NUM_SURF, std::vector<std::vector<Double_t> > (NUM_RCO, std::vector<Double_t> (AnitaClock::maxNumZcs, 0)));
925 std::vector<std::vector<std::vector<Int_t> > > sampZeroCrossings(NUM_SURF, std::vector<std::vector<Int_t> > (NUM_RCO, std::vector<Int_t> (AnitaClock::maxNumZcs, 0)));
927 for(Int_t surf=0; surf<NUM_SURF; surf++){
928 for(Int_t rco=0; rco<NUM_RCO; rco++){
929 for(Int_t zc=0; zc<AnitaClock::maxNumZcs; zc++){
930 measuredClockPeriods.at(surf).at(rco).at(zc) = 0;
938 std::vector<std::vector<Int_t> > numZcs(NUM_SURF, std::vector<Int_t>(NUM_RCO, 0));
940 for(Int_t surf=0; surf<NUM_SURF; surf++){
941 for(
int rco=0; rco<NUM_RCO; rco++){
942 numZcs.at(surf).at(rco) = getTimeOfUpwardsClockTicksCrossingZero(clockNumPoints[surf][rco],
944 clockTimes[surf][rco],
945 clockVolts[surf][rco],
946 timeZeroCrossings.at(surf).at(rco),
947 sampZeroCrossings.at(surf).at(rco),
950 for(Int_t zc=0; zc<numZcs.at(surf).at(rco); zc++){
952 measuredClockPeriods.at(surf).at(rco).at(zc-1) = (timeZeroCrossings.at(surf).at(rco).at(zc)
953 - timeZeroCrossings.at(surf).at(rco).at(zc-1));
975 std::vector<std::vector<std::vector<Double_t> > > nearestClockPeriod(NUM_SURF, std::vector<std::vector<Double_t> > (NUM_RCO, std::vector<Double_t>(AnitaClock::maxNumZcs, 0)));
977 std::vector<std::vector<Double_t> > differenceFromClockPeriod(NUM_SURF, std::vector<Double_t> (NUM_RCO, 0));
983 const Int_t dangerZoneStart = 170;
984 const Int_t dangerZoneEnd = 220;
987 for(Int_t surf=0; surf<NUM_SURF; surf++){
988 for(
int rco=0; rco<NUM_RCO; rco++){
989 for(
int zc=0; zc<numZcs.at(surf).at(rco)-1; zc++){
992 Double_t dt = measuredClockPeriods.at(surf).at(rco).at(zc);
994 std::cerr <<
"Idiot " << __FILE__ <<
": " << __LINE__ << std::endl;
997 Int_t sampZc = sampZeroCrossings.at(surf).at(rco).at(zc);
998 if(sampZc < 0 || sampZc >= NUM_SAMP){
999 std::cerr <<
"sampZeroCrossings Array!" << __FILE__ <<
": " << __LINE__ << std::endl;
1001 Int_t capNum = clockCapacitorNums[surf][rco][sampZc];
1005 if(capNum < dangerZoneStart || capNum > dangerZoneEnd){
1006 if(TMath::Abs(dt - AnitaClock::lowPeriodNs) < TMath::Abs(dt - AnitaClock::highPeriodNs)){
1007 differenceFromClockPeriod.at(surf).at(rco) += TMath::Abs(dt - AnitaClock::lowPeriodNs);
1008 nearestClockPeriod.at(surf).at(rco).at(zc) = AnitaClock::lowPeriodNs;
1013 differenceFromClockPeriod.at(surf).at(rco) += TMath::Abs(dt - AnitaClock::highPeriodNs);
1014 nearestClockPeriod.at(surf).at(rco).at(zc) = AnitaClock::highPeriodNs;
1021 if(numZcs.at(surf).at(rco) > 0){
1022 differenceFromClockPeriod.at(surf).at(rco)/=numZcs.at(surf).at(rco);
1032 Int_t chanIndex = surf*NUM_CHAN + 8;
1035 if(firstHitBus >= firstHitBusRcoLatchLimit || lastHitBus - firstHitBus > NUM_SAMP/2){
1042 if(differenceFromClockPeriod.at(surf).at(0) < differenceFromClockPeriod.at(surf).at(1)){
1060 std::vector<Int_t> zeroCrossingMatchIndices;
1061 zeroCrossingMatchIndices.clear();
1062 zeroCrossingMatchIndices.assign(NUM_SURF, 0);
1064 const Double_t halfClockPeriod = 0.5*AnitaClock::meanPeriodNs;
1065 for(Int_t surf=0; surf<NUM_SURF; surf++){
1068 if(TMath::Abs(timeZeroCrossings.at(surf).at(rco).at(0) - timeZeroCrossings.at(0).at(rco).at(0)) < halfClockPeriod){
1069 zeroCrossingMatchIndices.at(surf) = 0;
1072 else if(timeZeroCrossings.at(surf).at(rco).at(0) - timeZeroCrossings.at(0).at(rco).at(0) >= halfClockPeriod){
1076 zeroCrossingMatchIndices.at(surf) = -1;
1078 else if(timeZeroCrossings.at(surf).at(rco).at(0) - timeZeroCrossings.at(0).at(rco).at(0) <= halfClockPeriod){
1080 zeroCrossingMatchIndices.at(surf) = 1;
1093 Int_t startIndex = -1*TMath::MaxElement(NUM_SURF, &zeroCrossingMatchIndices[0]);
1099 const Int_t maxNumOffsetZcs = AnitaClock::maxNumZcs - startIndex;
1100 std::vector<Int_t> numHigh(maxNumOffsetZcs, 0);
1101 std::vector<Int_t> numLow(maxNumOffsetZcs, 0);
1102 std::vector<Int_t> meanClockPeriod(maxNumOffsetZcs, 0);
1103 std::vector<Int_t> count(maxNumOffsetZcs, 0);
1105 Int_t alignedPeriodIndex = 0;
1106 for(Int_t zcIndex=startIndex; zcIndex < AnitaClock::maxNumZcs; zcIndex++){
1107 numHigh.at(alignedPeriodIndex)=0;
1108 numLow.at(alignedPeriodIndex)=0;
1109 for(Int_t surf=0; surf<NUM_SURF; surf++){
1111 Int_t zcThisSurf = zcIndex + zeroCrossingMatchIndices.at(surf);
1112 if(zcThisSurf >=0 && zcThisSurf < AnitaClock::maxNumZcs && nearestClockPeriod.at(surf).at(rco).at(zcThisSurf) > 0){
1114 meanClockPeriod.at(zcThisSurf) += measuredClockPeriods.at(surf).at(rco).at(zcThisSurf);
1115 count.at(zcThisSurf)++;
1130 alignedPeriodIndex++;
1136 const Int_t numAlignedPeriodIndices = alignedPeriodIndex;
1137 std::vector<Double_t> mostCommonClockPeriod;
1138 mostCommonClockPeriod.clear();
1139 mostCommonClockPeriod.assign(maxNumOffsetZcs, 0);
1141 for(Int_t alignedPeriodIndex=0; alignedPeriodIndex<numAlignedPeriodIndices; alignedPeriodIndex++){
1143 if(count.at(alignedPeriodIndex)){
1144 meanClockPeriod.at(alignedPeriodIndex)/=count.at(alignedPeriodIndex);
1145 if(TMath::Abs(meanClockPeriod.at(alignedPeriodIndex) - AnitaClock::lowPeriodNs) < TMath::Abs(meanClockPeriod.at(alignedPeriodIndex) - AnitaClock::highPeriodNs)){
1146 mostCommonClockPeriod.at(alignedPeriodIndex) = AnitaClock::lowPeriodNs;
1149 mostCommonClockPeriod.at(alignedPeriodIndex) = AnitaClock::highPeriodNs;
1152 if(TMath::Abs(meanClockPeriod.at(alignedPeriodIndex) - 30) > 1){
1157 mostCommonClockPeriod.at(alignedPeriodIndex) = -1000;
1174 for(Int_t surf=0; surf<NUM_SURF; surf++){
1175 for(
int rco=0; rco<NUM_RCO; rco++){
1176 Int_t alignedPeriodIndex = 0;
1177 for(
int zcIndex=startIndex; zcIndex<startIndex; zcIndex++){
1178 Int_t zc = zcIndex + zeroCrossingMatchIndices.at(surf);
1180 if(zc >= 0 && zc < numZcs.at(surf).at(rco)-1 && mostCommonClockPeriod.at(alignedPeriodIndex)>0 ){
1182 Double_t dt = measuredClockPeriods.at(surf).at(rco).at(zc);
1185 std::cerr <<
"Idiot " << __FILE__ <<
": " << __LINE__ << std::endl;
1188 Int_t sampZc = sampZeroCrossings.at(surf).at(rco).at(zc);
1189 if(sampZc < 0 || sampZc >= clockNumPoints[surf][rco]){
1190 std::cerr <<
"sampZeroCrossings Array!" << __FILE__ <<
": " << __LINE__ << std::endl;
1192 Int_t capNum = clockCapacitorNums[surf][rco][sampZc];
1194 if(capNum < dangerZoneStart || capNum > dangerZoneEnd){
1195 differenceFromClockPeriod.at(surf).at(rco) += TMath::Abs(dt - mostCommonClockPeriod.at(alignedPeriodIndex));
1199 if(numZcs.at(surf).at(rco) > 0){
1200 differenceFromClockPeriod.at(surf).at(rco)/=numZcs.at(surf).at(rco);
1209 Int_t chanIndex = surf*NUM_CHAN + 8;
1212 if(firstHitBus >= firstHitBusRcoLatchLimit || lastHitBus - firstHitBus > NUM_SAMP/2){
1219 if(differenceFromClockPeriod.at(surf).at(0) < differenceFromClockPeriod.at(surf).at(1)){
1233 Int_t AnitaEventCalibrator::getTimeOfUpwardsClockTicksCrossingZero(Int_t numPoints, Int_t surf, Double_t* times, Double_t* volts, std::vector<Double_t>& timeZeroCrossings, std::vector<Int_t>& sampZeroCrossings,
bool raiseFlagIfClocksAreWeird){
1236 std::vector<Double_t> tZcs;
1237 std::vector<Int_t> sampZcs;
1238 std::vector<Int_t> prevExtremas;
1239 std::vector<Int_t> nextExtremas;
1241 std::vector<Int_t> maximaSamps;
1242 std::vector<Int_t> minimaSamps;
1245 findExtremaSamples(numPoints, volts, maximaSamps, minimaSamps);
1248 for(Int_t samp=0; samp<numPoints-1; samp++){
1249 Double_t y1 = volts[samp];
1250 Double_t y2 = volts[samp+1];
1251 Double_t t1 = times[samp];
1252 Double_t t2 = times[samp+1];
1253 if(y1 <= 0 && y2 > 0){
1256 Double_t tzc = getTimeOfZeroCrossing(t1, y1, t2, y2);
1257 if(TMath::IsNaN(tzc)){
1258 std::cerr <<
"Error in " __FILE__ <<
": line " << __LINE__ << std::endl;
1259 std::cerr << samp <<
"\t" << numPoints <<
"\t" << t1 <<
"\t" 1260 << y1 <<
"\t" << t2 <<
"\t" << y2 << std::endl;
1276 Int_t nextMaxima = numPoints-1;
1277 Int_t prevMaxima = 0;
1278 for(UInt_t maxInd=0; maxInd < maximaSamps.size(); maxInd++){
1279 if(maximaSamps.at(maxInd) > samp){
1283 if(maximaSamps.at(maxInd) > samp+1){
1284 nextMaxima = maximaSamps.at(maxInd);
1286 else if(maxInd < maximaSamps.size()-1){
1287 nextMaxima = maximaSamps.at(maxInd+1);
1293 prevMaxima = maximaSamps.at(maxInd-1);
1301 Int_t nextMinima = numPoints-1;
1302 Int_t prevMinima = 0;
1303 for(UInt_t minInd=0; minInd < minimaSamps.size(); minInd++){
1304 if(minimaSamps.at(minInd) > samp){
1306 nextMinima = minimaSamps.at(minInd);
1310 if(minInd > 0 && minimaSamps.at(minInd-1) < samp){
1311 prevMinima = minimaSamps.at(minInd-1);
1313 else if(minInd > 1 && minimaSamps.at(minInd-2) < samp){
1314 prevMinima = minimaSamps.at(minInd-2);
1323 Int_t prevExtrema = prevMinima > prevMaxima ? prevMinima : prevMaxima;
1324 Int_t nextExtrema = nextMinima < nextMaxima ? nextMinima : nextMaxima;
1337 if(volts[nextExtrema] - volts[prevExtrema] > AnitaClock::upgoingThreshold){
1340 prevExtremas.push_back(prevExtrema);
1341 nextExtremas.push_back(nextExtrema);
1343 tZcs.push_back(tzc);
1344 sampZcs.push_back(samp);
1352 if(raiseFlagIfClocksAreWeird==
true){
1353 if(tZcs.size() > (UInt_t)AnitaClock::maxNumZcs || tZcs.size() < (UInt_t)AnitaClock::minNumZcs){
1368 for(Int_t zc=0; zc<AnitaClock::maxNumZcs; zc++){
1369 if(zc < (Int_t)tZcs.size()){
1370 timeZeroCrossings.at(zc) = tZcs.at(zc);
1371 sampZeroCrossings.at(zc) = sampZcs.at(zc);
1381 void AnitaEventCalibrator::findExtremaSamples(Int_t length, Double_t* volts,
1382 std::vector<Int_t>& maximaSamps,
1383 std::vector<Int_t>& minimaSamps){
1385 maximaSamps.clear();
1386 minimaSamps.clear();
1388 for(
int samp=0; samp<length; samp++){
1389 Double_t y0 = samp > 0 ? volts[samp-1] : 0;
1390 Double_t y1 = volts[samp];
1393 Double_t y2 = samp < length-1 ? volts[samp + posOffset] : 0;
1394 while(y2==y1 && samp + posOffset < length){
1395 y2 = samp < length-1 ? volts[samp + posOffset] : 0;
1400 if(y0 > y1 && y1 < y2){
1401 minimaSamps.push_back(samp);
1403 else if(y0 < y1 && y1 > y2){
1404 maximaSamps.push_back(samp);
1410 Double_t AnitaEventCalibrator::getTimeOfZeroCrossing(Double_t x1, Double_t y1, Double_t x2, Double_t y2){
1413 Double_t m = (y1-y2)/(x1-x2);
1414 Double_t c = y1 - m*x1;
1429 Bool_t fApplyTempCorrection, Bool_t fAddPedestal,
1431 Double_t* tArray, Int_t* cArray) {
1438 Int_t chanIndex = surf*CHANNELS_PER_SURF + chan;
1440 Int_t numExtras = 0;
1441 Int_t labChip = eventPtr->
getLabChip(chanIndex);
1445 Double_t tempFactor = 1;
1446 if(fApplyTempCorrection==
true){
1451 if(earliestSample==0){
1456 if(latestSample==0){
1460 Short_t* rawArray = eventPtr->
data[chanIndex];
1468 if(latestSample<earliestSample) {
1471 Int_t nextExtra=256;
1472 Double_t extraTime=0;
1474 if(earliestSample<256) {
1476 for(Int_t samp = earliestSample;samp<256;samp++) {
1477 Int_t binRco = 1-rco;
1478 cArray[index] = samp;
1479 mvArray[index] = rawArray[samp];
1480 if(fAddPedestal==
true){
1481 mvArray[index] += fPedStruct.
thePeds[surf][labChip][chan][samp];
1483 tArray[index] = time;
1487 extraTime = time+(
deltaTs[surf][labChip][binRco][samp])*tempFactor;
1490 time += (
deltaTs[surf][labChip][binRco][samp])*tempFactor;
1495 time +=
epsilons[surf][labChip][rco]*tempFactor;
1499 time += (
deltaTs[surf][labChip][rco][0])*tempFactor;
1521 for(Int_t samp=1;samp<=latestSample;samp++) {
1524 if(nextExtra<260 && samp==1) {
1526 if(extraTime<time-0.22) {
1530 cArray[index] = nextExtra;
1531 mvArray[index] = Double_t(rawArray[nextExtra]);
1532 tArray[index] = extraTime;
1533 if(nextExtra < 259) {
1534 extraTime += (
deltaTs[surf][labChip][binRco][nextExtra])*tempFactor;
1546 cArray[index] = samp;
1547 mvArray[index] = Double_t(rawArray[samp]);
1548 tArray[index] = time;
1551 time+=(
deltaTs[surf][labChip][binRco][samp])*tempFactor;
1560 for(Int_t samp=earliestSample; samp<=latestSample; samp++){
1562 cArray[index] = samp;
1563 mvArray[index] = rawArray[samp];
1564 tArray[index] = time;
1566 time += (
deltaTs[surf][labChip][binRco][samp])*tempFactor;
1578 void AnitaEventCalibrator::loadCalib() {
1579 char calibDir[FILENAME_MAX];
1580 char fileName[FILENAME_MAX];
1581 char *calibEnv=getenv(
"ANITA_CALIB_DIR");
1583 char *utilEnv=getenv(
"ANITA_UTIL_INSTALL_DIR");
1585 sprintf(calibDir,
"calib");
1587 sprintf(calibDir,
"%s/share/anitaCalib",utilEnv);
1590 strncpy(calibDir,calibEnv,FILENAME_MAX);
1594 for(Int_t surf=0;surf<NUM_SURF;surf++) {
1595 for(Int_t chan=0;chan<NUM_CHAN;chan++) {
1596 for(Int_t chip=0;chip<NUM_CHIP;chip++) {
1604 for(Int_t surf=0;surf<NUM_SURF;surf++) {
1605 for(Int_t chip=0;chip<NUM_CHIP;chip++) {
1606 for(Int_t rco=0;rco<NUM_RCO;rco++) {
1607 epsilons[surf][chip][rco]=1.25*(rco+1);
1608 for(Int_t samp=0;samp<NUM_SAMP;samp++)
1609 deltaTs[surf][chip][rco][samp]=1./2.6;
1617 Int_t surf,chan,chip,rco,samp;
1619 sprintf(fileName,
"%s/%s",calibDir, voltageCalibFiles[AnitaVersion::get()]);
1620 std::ifstream CalibFile(fileName);
1621 char firstLine[180];
1622 CalibFile.getline(firstLine,179);
1624 while(CalibFile >> surf >> chan >> chip >> calib) {
1637 sprintf(fileName,
"%s/justBinByBin.dat",calibDir);
1638 std::ifstream binByBinCalibFile(fileName);
1639 binByBinCalibFile.getline(firstLine,179);
1640 while(binByBinCalibFile >> surf >> chip >> rco >> samp >> calib) {
1641 deltaTs[surf][chip][rco][samp]=calib;
1647 sprintf(fileName,
"%s/epsilonFromBenS.dat",calibDir);
1648 std::ifstream epsilonFile(fileName);
1649 epsilonFile.getline(firstLine,179);
1650 while(epsilonFile >> surf >> chip >> rco >> calib) {
1654 sprintf(fileName,
"%s/%s",calibDir, relativeCableDelayFiles[AnitaVersion::get()]);
1655 std::ifstream relativeCableDelayFile(fileName);
1656 relativeCableDelayFile.getline(firstLine,179);
1657 while(relativeCableDelayFile >> surf >> chan >> chip >> calib) {
1663 sprintf(fileName,
"%s/%s", calibDir, relativePhaseCenterToAmpaDelaysFiles[AnitaVersion::get()]);
1664 std::ifstream relativePhaseCenterToAmpaDelaysFile(fileName);
1665 relativePhaseCenterToAmpaDelaysFile.getline(firstLine,179);
1666 while(relativePhaseCenterToAmpaDelaysFile >> surf >> chan >> calib) {
1671 sprintf(fileName,
"%s/clockKeep.dat",calibDir);
1672 std::ifstream clockKeep(fileName);
1673 clockKeep.getline(firstLine,179);
1674 while(clockKeep >> surf >> chip >> calib) {
1678 sprintf(fileName,
"%s/peds.dat",calibDir);
1679 std::ifstream PedestalFile(fileName,std::ios::in | std::ios::binary);
1683 sprintf(fileName,
"%s/RFCalibration_BRotter.txt",calibDir);
1684 std::ifstream BRotterRfPowPeds(fileName);
1685 std::string chanName;
1686 Double_t rfYInt,ampNoise,chanGain,rfSlope;
1688 BRotterRfPowPeds.getline(firstLine,179);
1689 while(BRotterRfPowPeds >> chanName >> surfi >> chani >> rfSlope >> rfYInt >> ampNoise >> chanGain) {
1690 RfPowYInt[surfi-1][chani-1]=rfYInt;
1691 RfPowSlope[surfi-1][chani-1]=rfSlope;
1696 Double_t AnitaEventCalibrator::convertRfPowTodBm(
int surf,
int chan,
int adc){
1697 return (
double(adc)-RfPowYInt[surf][chan])/RfPowSlope[surf][chan];
1700 Double_t AnitaEventCalibrator::convertRfPowToKelvin(
int surf,
int chan,
int adc){
1701 double dBm = AnitaEventCalibrator::convertRfPowTodBm(surf, chan, adc);
1702 double mW = TMath::Power(10,dBm/10.);
1703 double K = (mW/(1000.*1.38e-23*1e9));
Double_t fTempFactorGuesses[12]
A holder variable to cling on to the temperature correction factor that we are guessing at...
deltaTs, voltage, unwrap, trigger jitter, cable delay. The full monty.
Int_t numPointsArray[12]
Number of samples in each channel.
std::vector< std::vector< RingBuffer > > clockPeriodRingBuffers
Holds rolling average of temperature correction.
Inter-SURF timing (trigger jitter) without cable delay.
Int_t getRcoCorrected(int chanIndex)
Returns firmware RCO after correcting for latch delay (and factor of -1 for different definitions of ...
Double_t clockKeepTime[12][4]
How much time after clock up-tick to keep, calib food.
All the timing of kFull, but none of the voltage calibration (Ped corrected ADC counts) ...
enum WaveCalType::EWaveCalType WaveCalType_t
The calibration enumeration type.
static AnitaEventCalibrator * Instance(int version=0)
Instance generator.
std::map< Double_t, TGraph * > grClock0s
Need to process clock 0 depending on needs of other SURF.
double fVolts[12 *9][260]
Array of unwrapped (unless kNoCalib) voltages for each channel.
Double_t epsilons[12][4][2]
Calib constants: time (ns) for write pointer to go from sample 255 -> 0 (in ANITA-2 and ANITA-3 with ...
int fNumPoints[12 *9]
Number of poins per channel.
Double_t deltaTs[12][4][2][260]
Calib constants: The time for the write pointer to travel between successove capacitors.
Double_t dtInterp
Interpolating clock for alignment step.
Useful for looping over all calibrations.
Int_t calibrateUsefulEvent(UsefulAnitaEvent *eventPtr, WaveCalType::WaveCalType_t calType)
Calibration Routine The routine that is used to calibrate the voltage time waveforms in a UsefulAnita...
UChar_t chipIdFlag[12 *9]
chipIdFlag
AnitaEventCalibrator – The ANITA Event Calibrator.
std::vector< Int_t > defaultClocksToAlign
List of SURFs for getClockAlignment() (for calibration progs)
void updateTemperatureCorrection(UsefulAnitaEvent *eventPtr)
Update RingBuffer for this event.
Double_t voltsArray[12][9][260]
Channel volts in mV.
void getTempFactors(UsefulAnitaEvent *eventPtr)
Interface to RingBuffer of clock periods for temperature correction.
Int_t fClockProblem
Flag raised if more than 4 upgoing zero crossings in clock, won't update temp correction. RCO guessing may also be negatively affected by this.
Short_t data[12 *9][260]
The pedestal subtracted waveform data. Note that these arrays must be unwrapped and calibrated to bec...
int fCapacitorNum[12 *9][260]
Array of capacitor numbers.
std::vector< TGraph * > grClockInterps
Interpolated clocks.
Int_t getLastHitBus(Int_t chanIndex) const
Returns the lastHitbus value for the channel.
UsefulAnitaEvent – The Calibrated Useful Anita Event object.
For calibration: sample-to-sample dts without unwrapping (or voltage calibs)
The 260 samples straight from raw data.
Int_t getFirstHitBus(Int_t chanIndex) const
Returns the firstHitbus value for the channel.
void guessRco(UsefulAnitaEvent *eventPtr)
Guess RCO from clock.
Int_t getLabChip(Int_t chanIndex) const
Returns the LABRADOR number.
Int_t getEarliestSample(Int_t chanIndex)
Returns the earliest sample in the waveform.
Double_t relativeCableDelays[12][9][4]
From AMPA inputs to digizier delays.
Int_t unwrapChannel(UsefulAnitaEvent *eventPtr, Int_t surf, Int_t chan, Int_t rco, Bool_t fApplyTempCorrection, Bool_t fAddPedestal, Double_t *voltsArray, Double_t *timeArray, Int_t *scaArray)
Double_t nominalDeltaT
If we don't want bin-to-bin deltaTs.
Double_t relativePhaseCenterToAmpaDelays[12][9]
From phase center to AMPAs (hopefully)
For calib: opposite RCO from software algorithm.
unsigned short thePeds[12][4][9][260]
mean pedestal
Double_t timeArray[12][260]
Channel times in ns.
Int_t fRFSpike
Flag raised if the ADC value is too large or small in RF.
WaveCalType::WaveCalType_t fCalType
The calibration type requested.
The X good samples from raw data (260-hitbus)
Int_t fRcoArray[12]
An array to store the guessed at RCO values.
For calib: applies RCO from firmware (no latch delay)
Int_t fClockProblem
Flag raised if more than 4 or less than 2 upgoing zero crossings in a SURF clock. ...
Int_t scaArray[12][260]
Capacitor numbers for each sample.
Int_t fFromCalibratedAnitaEvent
Flag used in determining whether the event came from a CalibratedAnitaEvent.
For calib: 1-firmware RCO (no latch delay)
No inter-SURF timing (or zero meaning)
Double_t mvCalibVals[12][9][4]
Calib constants: converts from ADC counts to millivolts.
enum AnitaPol::EAnitaPol AnitaPol_t
Polarisation enumeration.
Faster, but no algorithm for it.
std::vector< Double_t > tempFactors
Multiplicative factor for deltaTs & epsilons accounting for temperature.
Double_t fClockPhiArray[12]
An array to store the derived clock calibration numbers (from aligning the clocks) ...
std::vector< Int_t > rcoVector
The output of AnitaEventCalibrator::guessRco() goes here.
Int_t fClockSpike
Flag raised if the ADC value is too large or small in clock.
Using mV/ADC = 1 and all dts = 1./2.6 ns.
Int_t getLatestSample(Int_t chanIndex)
Returns the latest sample in the waveform.
double fTimes[12 *9][260]
Array of unwrapped (unless kNoCalib) times for each channel.
Remove the spiky clock in early stage.