pxar
 All Classes Namespaces Functions Variables Typedefs Friends
PixTestSetTrim.cc
1 // -- author: Daniel Pitzl
2 // set Vtrim and trim bits
3 
4 #include <cmath> // sqrt
5 #include <stdlib.h> // atof, atoi
6 #include <algorithm> // std::find
7 
8 #include "PixTestSetTrim.hh"
9 #include "log.h"
10 
11 using namespace std;
12 using namespace pxar;
13 
14 ClassImp(PixTestSetTrim)
15 
16 //------------------------------------------------------------------------------
17 PixTestSetTrim::PixTestSetTrim( PixSetup *a, std::string name )
18 : PixTest(a, name), fParVcal(-1), fParNtrig(-1)
19 {
20  PixTest::init();
21  init();
22  LOG(logDEBUG) << "PixTestSetTrim ctor(PixSetup &a, string, TGTab *)";
23 }
24 
25 //------------------------------------------------------------------------------
26 PixTestSetTrim::PixTestSetTrim() : PixTest()
27 {
28  LOG(logDEBUG) << "PixTestSetTrim ctor()";
29 }
30 
31 //------------------------------------------------------------------------------
32 bool PixTestSetTrim::setParameter( string parName, string sval )
33 {
34  bool found(false);
35 
36  for( uint32_t i = 0; i < fParameters.size(); ++i ) {
37 
38  if( fParameters[i].first == parName ) {
39 
40  found = true;
41 
42  sval.erase(remove(sval.begin(), sval.end(), ' '), sval.end());
43 
44  if( !parName.compare( "targetvcal" ) )
45  fParVcal = atoi( sval.c_str() );
46 
47  if( !parName.compare( "ntrig" ) )
48  fParNtrig = atoi( sval.c_str() );
49 
50  setToolTips();
51  break;
52  }
53  }
54  return found;
55 }
56 
57 //------------------------------------------------------------------------------
58 void PixTestSetTrim::init()
59 {
60  LOG(logDEBUG) << "PixTestSetTrim::init()";
61 
62  fDirectory = gFile->GetDirectory( fName.c_str() );
63  if( !fDirectory ) {
64  fDirectory = gFile->mkdir( fName.c_str() );
65  }
66  fDirectory->cd();
67 }
68 
69 //------------------------------------------------------------------------------
71 {
72  fTestTip = string( "set Vtrim and trim bits to get TargetVcal threshold")
73  ;
74  fSummaryTip = string("summary plot to be implemented")
75  ;
76 
77 }
78 
79 //------------------------------------------------------------------------------
80 void PixTestSetTrim::bookHist(string name)
81 {
82  LOG(logDEBUG) << "nothing done with " << name;
83 }
84 
85 //------------------------------------------------------------------------------
86 PixTestSetTrim::~PixTestSetTrim()
87 {
88  LOG(logDEBUG) << "PixTestSetTrim dtor";
89  std::list<TH1*>::iterator il;
90  fDirectory->cd();
91  for( il = fHistList.begin(); il != fHistList.end(); ++il ) {
92  LOG(logINFO) << "Write out " << (*il)->GetName();
93  (*il)->SetDirectory(fDirectory);
94  (*il)->Write();
95  }
96 }
97 
98 //------------------------------------------------------------------------------
99 // Daniel Pitzl, DESY, 25.1.2014: measure ROC threshold map vs Vcal
100 
101 void PixTestSetTrim::RocThrMap( uint8_t roc, uint32_t nTrig,
102  bool xtalk, bool cals )
103 {
104  if( roc > 15 ) {
105  LOG(logERROR) << "[PixTestSetTrim::RocThrMap] invalid roc " << roc;
106  return;
107  }
108 
109  fApi->_dut->testAllPixels( true, roc );
110 
111  for( uint8_t col = 0; col < 52; ++col )
112  for( uint8_t row = 0; row < 80; ++row ) {
113  uint8_t trim = modtrm[roc][col][row];
114  // fApi->_dut->trimPixel( col, row, trim, roc ); // DP
115  fApi->_dut->updateTrimBits( col, row, trim, roc );
116  }
117 
118  // measure:
119 
120  uint16_t flags = FLAG_RISING_EDGE;
121  if( xtalk ) flags |= FLAG_XTALK;
122  if( cals ) flags |= FLAG_CALS;
123 
124  vector<pixel> vpix = fApi->getThresholdMap( "Vcal", flags, nTrig );
125 
126  LOG(logINFO) << "vpix.size() " << vpix.size();
127 
128  // book maps per ROC:
129 
130  TH2D *h2(0);
131  TH1D *h1(0);
132 
133  static uint32_t iter = 0;
134 
135  h2 = new TH2D( Form( "Threshold_map_ROC_%d_i%i", int(roc), iter ),
136  Form( "Threshold map ROC %d i%i", int(roc), iter ),
137  52, -0.5, 51.5, 80, -0.5, 79.5 );
138  h2->SetMinimum(0);
139  h2->SetMaximum(256);
140  setTitles( h2, "col", "row" );
141  h2->GetZaxis()->SetTitle( "Vcal threshold [DAC]" );
142  h2->SetStats(0);
143  fHistList.push_back(h2);
144 
145  h1 = new TH1D( Form( "ThrDistribution_C%d_i%i", int(roc), iter ),
146  Form( "Threshold distribution ROC %d i%i", int(roc), iter ),
147  256, -0.5, 255.5 );
148  setTitles( h1, "Vcal threshold [DAC]", "pixels" );
149  h1->SetStats(1);
150  fHistList.push_back(h1);
151 
152  // data:
153 
154  for( size_t ipx = 0; ipx < vpix.size(); ++ipx ) {
155  if( vpix[ipx].roc() == roc ) {
156  h2->Fill( vpix[ipx].column(), vpix[ipx].row(), vpix[ipx].value());
157  h1->Fill( vpix[ipx].value());
158  if( vpix[ipx].column() < 52 && vpix[ipx].row() < 80 )
159  modthr[roc][vpix[ipx].column()][vpix[ipx].row()] = (uint8_t)vpix[ipx].value();
160  }
161  }
162 
163  h2->Draw("colz");
164  PixTest::update();
165 
166  fDisplayedHist = find( fHistList.begin(), fHistList.end(), h2 );
167 
168  fApi->_dut->testAllPixels( false, roc );
169 
170  iter++;
171 
172 } // RocThrMap
173 
174 //------------------------------------------------------------------------------
175 // Daniel Pitzl, DESY, 25.1.2014: print ROC threshold map
176 
177 void PixTestSetTrim::printThrMap( uint8_t roc, int &nok )
178 {
179  int sum = 0;
180  nok = 0;
181  int su2 = 0;
182  int vmin = 255;
183  int vmax = 0;
184  int colmin = -1;
185  int rowmin = -1;
186  int colmax = -1;
187  int rowmax = -1;
188 
189  cout << "Threshold map for ROC " << roc << endl;
190  for( int row = 79; row >= 0; --row ) {
191  cout << setw(2) << row << ":";
192  for( int col = 0; col < 52; ++col ) {
193 
194  int thr = modthr[roc][col][row];
195  cout << " " << thr;
196  if( col == 25 ) cout << endl << " ";
197 
198  if( thr < 255 ) {
199  sum += thr;
200  su2 += thr*thr;
201  nok++;
202  }
203  if( thr > 0 && thr < vmin ) {
204  vmin = thr;
205  colmin = col;
206  rowmin = row;
207  }
208  if( thr > vmax && thr < 255 ) {
209  vmax = thr;
210  colmax = col;
211  rowmax = row;
212  }
213  } // cols
214  cout << endl;
215  } // rows
216 
217  cout << "valid thresholds " << nok << endl;
218  if( nok > 0 ) {
219  cout << "min thr " << vmin << " at " << colmin << " " << rowmin << endl;
220  cout << "max thr " << vmax << " at " << colmax << " " << rowmax << endl;
221  double mid = (double)sum / (double) nok;
222  double rms = sqrt( (double)su2 / (double)nok - mid*mid );
223  cout << "mean thr " << mid
224  << ", rms " << rms
225  << endl;
226  }
227  cout.flush();
228 
229 } // printThrMap
230 
231 //------------------------------------------------------------------------------
232 // Daniel Pitzl, DESY, 25.1.2014: trim bit correction
233 
234 void PixTestSetTrim::TrimStep( int roc, int target, int correction,
235  int nTrig, int xtalk, int cals )
236 {
237  LOG(logINFO) << "TrimStep for ROC " << roc
238  << " with correction " << correction;
239 
240  for( int col = 0; col < 52; ++col ) {
241  for( int row = 0; row < 80; ++row ) {
242 
243  int thr = modthr[roc][col][row];
244  rocthr[col][row] = thr; // remember
245 
246  int trim = modtrm[roc][col][row];
247  roctrm[col][row] = trim; // remember
248 
249  if( thr > target && thr < 255 )
250  trim -= correction; // make softer
251  else
252  trim += correction; // make harder
253 
254  if( trim < 0 ) trim = 0;
255  if( trim > 15 ) trim = 15;
256 
257  modtrm[roc][col][row] = trim;
258 
259  } // rows
260  } // cols
261 
262  // measure new result:
263 
264  RocThrMap( roc, nTrig, xtalk, cals ); // fills modthr[roc][][]
265 
266  for( int col = 0; col < 52; ++col ) {
267  for( int row = 0; row < 80; ++row ) {
268 
269  int thr = modthr[roc][col][row];
270 
271  int old = rocthr[col][row];
272 
273  if( abs( thr - target ) > abs( old - target ) ) {
274  modtrm[roc][col][row] = roctrm[col][row]; // go back
275  modthr[roc][col][row] = old;
276  }
277 
278  } // rows
279  } // cols
280 
281 } // TrimStep
282 
283 //------------------------------------------------------------------------------
285 {
286  LOG(logINFO) << "PixTestSetTrim::doTest() ntrig = " << fParNtrig;
287 
288  fDirectory->cd();
289  fHistList.clear();
290  PixTest::update();
291 
292  // global threshold map:
293 
294  for( size_t k = 0; k < 16; ++k )
295  for( size_t i = 0; i < 52; ++i )
296  for( size_t j = 0; j < 80; ++j ){
297  modthr[k][i][j] = 255; // thr, 255 = invalid
298  modtrm[k][i][j] = 15; // trim bits, 15 = off
299  }
300 
301  size_t nRocs = fPixSetup->getConfigParameters()->getNrocs();
302  bool cals = 0;
303  bool xtalk = 0;
304  uint16_t flags = FLAG_RISING_EDGE;
305  int nok = 0;
306 
307  uint8_t cal = fApi->_dut->getDAC( 0, "Vcal" );
308  uint8_t ctl = fApi->_dut->getDAC( 0, "CtrlReg" );
309 
310  fApi->setDAC( "CtrlReg", 0 ); // all ROCs small Vcal
311  LOG(logINFO) << "CtrlReg 0 (small Vcal)";
312 
313  for( size_t roc = 0; roc < nRocs; ++roc ) {
314 
315  LOG(logINFO) << "Trimming ROC " << roc;
316 
317  // measure un-trimmed threshold map:
318 
319  RocThrMap( roc, fParNtrig, xtalk, cals ); // fills modthr[roc][][]
320 
321  // find pixel with hardest threshold:
322 
323  int vmax = 0;
324  int maxcol = -1;
325  int maxrow = -1;
326 
327  for( int row = 79; row >= 0; --row ) {
328  for( int col = 0; col < 52; ++col ) {
329 
330  int thr = modthr[roc][col][row];
331  if( thr > vmax && thr < 255 ) {
332  vmax = thr;
333  maxcol = col;
334  maxrow = row;
335  }
336  } // cols
337  } // rows
338 
339  if( maxcol < 0 ) {
340  LOG(logWARNING) << "No valid threshold on ROC " << roc << ": skipped";
341  continue;
342  }
343  LOG(logINFO) << "max thr " << vmax
344  << " at " << maxcol << " " << maxrow;
345 
346  // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
347  // setVtrim using max pixel:
348 
349  fApi->_dut->testPixel( maxcol, maxrow, true, roc );
350 
351  uint8_t trim = 0; // 0 = strongest
352  // fApi->_dut->trimPixel( maxcol, maxrow, trim, roc ); // DP
353  fApi->_dut->updateTrimBits( maxcol, maxrow, trim, roc );
354 
355  int itrim = 1;
356  for( ; itrim < 254; itrim += 2 ) {
357 
358  fApi->setDAC( "Vtrim", itrim, roc );
359  vector<pixel> vpix9 = fApi->getThresholdMap( "Vcal", flags, fParNtrig );
360  int thr = 256;
361  for( size_t ipx = 0; ipx < vpix9.size(); ++ipx )
362  if( vpix9[ipx].roc() == roc &&
363  vpix9[ipx].column() == maxcol &&
364  vpix9[ipx].row() == maxrow )
365  thr = (int)vpix9[ipx].value();
366 
367  LOG(logINFO)
368  << "Vtrim " << setw(3) << itrim
369  << ": vpix9.size " << vpix9.size()
370  << ": " << (int) vpix9[0].roc()
371  << " " << (int) vpix9[0].column()
372  << " " << (int) vpix9[0].row()
373  << ", thr " << setw(3) << thr;
374  if( thr < fParVcal )
375  break;
376 
377  } // itrim
378 
379  //itrim += 2; // margin
380  fApi->setDAC( "Vtrim", itrim, roc );
381  LOG(logINFO) << "set Vtrim to " << itrim;
382 
383  // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
384  // iterate trim bits:
385 
386  for( int row = 79; row >= 0; --row )
387  for( int col = 0; col < 52; ++col ) {
388  modtrm[roc][col][row] = 7; // half way
389  rocthr[col][row] = modtrm[roc][col][row]; // remember
390  roctrm[col][row] = 15; // old
391  }
392 
393  LOG(logINFO) << "trim: measuring Vcal threshold map with trim 7";
394 
395  RocThrMap( roc, fParNtrig, xtalk, cals ); // uses modtrm, fills modthr
396 
397  printThrMap( roc, nok );
398 
399  int correction = 4;
400 
401  TrimStep( roc, fParVcal, correction,
402  fParNtrig, xtalk, cals ); // fills modtrm, fills modthr
403 
404  printThrMap( roc, nok );
405 
406  correction = 2;
407 
408  TrimStep( roc, fParVcal, correction,
409  fParNtrig, xtalk, cals ); // fills modtrm, fills modthr
410 
411  printThrMap( roc, nok );
412 
413  correction = 1;
414 
415  TrimStep( roc, fParVcal, correction,
416  fParNtrig, xtalk, cals ); // fills modtrm, fills modthr
417 
418  printThrMap( roc, nok );
419 
420  correction = 1;
421 
422  TrimStep( roc, fParVcal, correction,
423  fParNtrig, xtalk, cals ); // fills modtrm, fills modthr
424 
425  printThrMap( roc, nok );
426 
427  correction = 1;
428 
429  TrimStep( roc, fParVcal, correction,
430  fParNtrig, xtalk, cals ); // fills modtrm, fills modthr
431 
432  printThrMap( roc, nok );
433 
434  fApi->_dut->testPixel( maxcol, maxrow, false, roc );
435 
436  } // rocs
437 
438  fApi->setDAC( "Vcal", cal ); // restore on all ROCs
439  fApi->setDAC( "CtrlReg", ctl ); // restore
440  LOG(logINFO) << "back to Vcal " << int(cal);
441  LOG(logINFO) << "back to CtrlReg " << int(ctl);
442 
443  LOG(logINFO) << "PixTestSetTrim::doTest() done for " << nRocs << " ROCs";
444 }
bool setDAC(std::string dacName, uint8_t dacValue, uint8_t rocI2C)
Definition: api.cc:546
PixSetup * fPixSetup
all necessary stuff in one place
Definition: PixTest.hh:290
void doTest()
function connected to "DoTest" button of PixTab
void testPixel(uint8_t column, uint8_t row, bool enable)
Definition: dut.cc:432
std::vector< std::pair< std::string, std::string > > fParameters
the parameters of this test
Definition: PixTest.hh:302
bool updateTrimBits(std::vector< pixelConfig > trimming, uint8_t rocid)
Definition: dut.cc:551
TDirectory * fDirectory
where the root histograms will end up
Definition: PixTest.hh:306
void setToolTips()
implement this to provide updated tool tips if the user changes test parameters
dut * _dut
Definition: api.h:728
std::vector< pixel > getThresholdMap(std::string dacName, uint8_t dacStep, uint8_t dacMin, uint8_t dacMax, uint16_t flags, uint16_t nTriggers)
Definition: api.cc:1080
virtual bool setParameter(std::string parName, std::string sval)
set the string value of a parameter
void testAllPixels(bool enable)
Definition: dut.cc:503
std::list< TH1 * >::iterator fDisplayedHist
pointer to the histogram currently displayed
Definition: PixTest.hh:309
std::list< TH1 * > fHistList
list of histograms available in PixTab::next and PixTab::previous
Definition: PixTest.hh:307
void setTitles(TH1 *h, const char *sx, const char *sy, float size=0.05, float xoff=1.1, float yoff=1.1, float lsize=0.05, int font=42)
utility to set histogram titles
Definition: PixTest.cc:649
void update()
signal to PixTab to update the canvas
Definition: PixTest.cc:569
uint8_t getDAC(size_t rocId, std::string dacName)
Definition: dut.cc:314
pxar::pxarCore * fApi
pointer to the API
Definition: PixTest.hh:289
void init()
sets all test parameters
Definition: PixTest.cc:62