CMS 3D CMS Logo

SiPixelGenError.cc
Go to the documentation of this file.
1 //
2 // SiPixelGenError.cc Version 2.30
3 //
4 // Object stores Lorentz widths, bias corrections, and errors for the Generic Algorithm
5 //
6 // Created by Morris Swartz on 10/27/06.
7 // Add some debugging messages. d.k. 5/14
8 // Update for Phase 1 FPix, M.S. 1/15/17
9 // V2.01 - Allow subdetector ID=5 for FPix R2P2, Fix error message
10 // V2.10 - Update the variable size [SI_PIXEL_TEMPLATE_USE_BOOST] option so that it works with VI's enhancements
11 // V2.20 - Add directory path selection to the ascii pushfile method
12 // V2.21 - Move templateStore to the heap, fix variable name in pushfile()
13 // V2.30 - Fix interpolation of IrradiationBias corrections
14 
15 //#include <stdlib.h>
16 //#include <stdio.h>
17 #ifndef SI_PIXEL_TEMPLATE_STANDALONE
18 #include <cmath>
19 #else
20 #include <math.h>
21 #endif
22 #include <algorithm>
23 #include <vector>
24 //#include "boost/multi_array.hpp"
25 #include <iostream>
26 #include <iomanip>
27 #include <sstream>
28 #include <fstream>
29 #include <list>
30 
31 #ifndef SI_PIXEL_TEMPLATE_STANDALONE
35 #define LOGERROR(x) LogError(x)
36 #define LOGWARNING(x) LogWarning(x)
37 #define LOGINFO(x) LogInfo(x)
38 #define ENDL " "
40 using namespace edm;
41 #else
42 #include "SiPixelGenError.h"
43 #define LOGERROR(x) std::cout << x << ": "
44 #define LOGINFO(x) std::cout << x << ": "
45 #define LOGWARNING(x) std::cout << x << ": "
46 #define ENDL std::endl
47 #endif
48 
49 //****************************************************************
54 //****************************************************************
55 bool SiPixelGenError::pushfile(int filenum, std::vector<SiPixelGenErrorStore>& pixelTemp, std::string dir) {
56  // Add info stored in external file numbered filenum to theGenErrorStore
57 
58  // Local variables
59  int i, j, k;
60  float costrk[3] = {0, 0, 0};
61  const char* tempfile;
62  // char title[80]; remove this
63  char c;
64  const int code_version = {1};
65 
66  // Create a filename for this run
67 
68  std::ostringstream tout;
69 
70  // Create different path in CMSSW than standalone
71 
72 #ifndef SI_PIXEL_TEMPLATE_STANDALONE
73  tout << dir << "generror_summary_zp" << std::setw(4) << std::setfill('0') << std::right << filenum << ".out"
74  << std::ends;
75  std::string tempf = tout.str();
76  edm::FileInPath file(tempf.c_str());
77  tempfile = (file.fullPath()).c_str();
78 #else
79  tout << "generror_summary_zp" << std::setw(4) << std::setfill('0') << std::right << filenum << ".out" << std::ends;
80  std::string tempf = tout.str();
81  tempfile = tempf.c_str();
82 #endif
83 
84  // open the Generic file
85 
86  std::ifstream in_file(tempfile, std::ios::in);
87 
88  if (in_file.is_open()) {
89  // Create a local GenError storage entry
90 
91  SiPixelGenErrorStore theCurrentTemp;
92 
93  // Read-in a header string first and print it
94 
95  for (i = 0; (c = in_file.get()) != '\n'; ++i) {
96  if (i < 79) {
97  theCurrentTemp.head.title[i] = c;
98  }
99  }
100  if (i > 78) {
101  i = 78;
102  }
103  theCurrentTemp.head.title[i + 1] = '\0';
104  LOGINFO("SiPixelGenError") << "Loading Pixel GenError File - " << theCurrentTemp.head.title << ENDL;
105 
106  // next, the header information
107 
108  in_file >> theCurrentTemp.head.ID >> theCurrentTemp.head.templ_version >> theCurrentTemp.head.Bfield >>
109  theCurrentTemp.head.NTy >> theCurrentTemp.head.NTyx >> theCurrentTemp.head.NTxx >> theCurrentTemp.head.Dtype >>
110  theCurrentTemp.head.Vbias >> theCurrentTemp.head.temperature >> theCurrentTemp.head.fluence >>
111  theCurrentTemp.head.qscale >> theCurrentTemp.head.s50 >> theCurrentTemp.head.lorywidth >>
112  theCurrentTemp.head.lorxwidth >> theCurrentTemp.head.ysize >> theCurrentTemp.head.xsize >>
113  theCurrentTemp.head.zsize >> theCurrentTemp.head.ss50 >> theCurrentTemp.head.lorybias >>
114  theCurrentTemp.head.lorxbias >> theCurrentTemp.head.fbin[0] >> theCurrentTemp.head.fbin[1] >>
115  theCurrentTemp.head.fbin[2];
116 
117  if (in_file.fail()) {
118  LOGERROR("SiPixelGenError") << "Error reading file, no GenError load" << ENDL;
119  return false;
120  }
121 
122  LOGINFO("SiPixelGenError") << "GenError ID = " << theCurrentTemp.head.ID << ", GenError Version "
123  << theCurrentTemp.head.templ_version << ", Bfield = " << theCurrentTemp.head.Bfield
124  << ", NTy = " << theCurrentTemp.head.NTy << ", NTyx = " << theCurrentTemp.head.NTyx
125  << ", NTxx = " << theCurrentTemp.head.NTxx << ", Dtype = " << theCurrentTemp.head.Dtype
126  << ", Bias voltage " << theCurrentTemp.head.Vbias << ", temperature "
127  << theCurrentTemp.head.temperature << ", fluence " << theCurrentTemp.head.fluence
128  << ", Q-scaling factor " << theCurrentTemp.head.qscale << ", 1/2 multi dcol threshold "
129  << theCurrentTemp.head.s50 << ", 1/2 single dcol threshold " << theCurrentTemp.head.ss50
130  << ", y Lorentz Width " << theCurrentTemp.head.lorywidth << ", y Lorentz Bias "
131  << theCurrentTemp.head.lorybias << ", x Lorentz width " << theCurrentTemp.head.lorxwidth
132  << ", x Lorentz Bias " << theCurrentTemp.head.lorxbias
133  << ", Q/Q_avg fractions for Qbin defs " << theCurrentTemp.head.fbin[0] << ", "
134  << theCurrentTemp.head.fbin[1] << ", " << theCurrentTemp.head.fbin[2]
135  << ", pixel x-size " << theCurrentTemp.head.xsize << ", y-size "
136  << theCurrentTemp.head.ysize << ", zsize " << theCurrentTemp.head.zsize << ENDL;
137 
138  if (theCurrentTemp.head.templ_version < code_version) {
139  LOGERROR("SiPixelGenError") << "code expects version " << code_version << ", no GenError load" << ENDL;
140  return false;
141  }
142 
143 #ifdef SI_PIXEL_TEMPLATE_USE_BOOST
144 
145  // next, layout the 1-d/2-d structures needed to store GenError info
146 
147  theCurrentTemp.cotbetaY = new float[theCurrentTemp.head.NTy];
148  theCurrentTemp.cotbetaX = new float[theCurrentTemp.head.NTyx];
149  theCurrentTemp.cotalphaX = new float[theCurrentTemp.head.NTxx];
150 
151  theCurrentTemp.enty.resize(boost::extents[theCurrentTemp.head.NTy]);
152 
153  theCurrentTemp.entx.resize(boost::extents[theCurrentTemp.head.NTyx][theCurrentTemp.head.NTxx]);
154 
155 #endif
156 
157  // next, loop over all y-angle entries
158 
159  for (i = 0; i < theCurrentTemp.head.NTy; ++i) {
160  in_file >> theCurrentTemp.enty[i].runnum >> costrk[0] >> costrk[1] >> costrk[2];
161 
162  if (in_file.fail()) {
163  LOGERROR("SiPixelGenError") << "Error reading file 1, no GenError load, run # " << theCurrentTemp.enty[i].runnum
164  << ENDL;
165  return false;
166  }
167 
168  // Calculate the alpha, beta, and cot(beta) for this entry
169 
170  theCurrentTemp.enty[i].cotalpha = costrk[0] / costrk[2];
171 
172  theCurrentTemp.enty[i].cotbeta = costrk[1] / costrk[2];
173 
174  in_file >> theCurrentTemp.enty[i].qavg >> theCurrentTemp.enty[i].pixmax >> theCurrentTemp.enty[i].dyone >>
175  theCurrentTemp.enty[i].syone >> theCurrentTemp.enty[i].dxone >> theCurrentTemp.enty[i].sxone;
176 
177  if (in_file.fail()) {
178  LOGERROR("SiPixelGenError") << "Error reading file 2, no GenError load, run # " << theCurrentTemp.enty[i].runnum
179  << ENDL;
180  return false;
181  }
182 
183  in_file >> theCurrentTemp.enty[i].dytwo >> theCurrentTemp.enty[i].sytwo >> theCurrentTemp.enty[i].dxtwo >>
184  theCurrentTemp.enty[i].sxtwo >> theCurrentTemp.enty[i].qmin >> theCurrentTemp.enty[i].qmin2;
185 
186  if (in_file.fail()) {
187  LOGERROR("SiPixelGenError") << "Error reading file 3, no GenError load, run # " << theCurrentTemp.enty[i].runnum
188  << ENDL;
189  return false;
190  }
191 
192  if (theCurrentTemp.enty[i].qmin <= 0.) {
193  LOGERROR("SiPixelGenError") << "Error in GenError ID " << theCurrentTemp.head.ID
194  << " qmin = " << theCurrentTemp.enty[i].qmin << ", run # "
195  << theCurrentTemp.enty[i].runnum << ENDL;
196  return false;
197  }
198 
199  for (j = 0; j < 4; ++j) {
200  in_file >> theCurrentTemp.enty[i].yavggen[j] >> theCurrentTemp.enty[i].yrmsgen[j] >>
201  theCurrentTemp.enty[i].xavggen[j] >> theCurrentTemp.enty[i].xrmsgen[j];
202 
203  if (in_file.fail()) {
204  LOGERROR("SiPixelGenError") << "Error reading file 14a, no GenError load, run # "
205  << theCurrentTemp.enty[i].runnum << ENDL;
206  return false;
207  }
208  }
209  }
210 
211  // next, loop over all barrel x-angle entries
212 
213  for (k = 0; k < theCurrentTemp.head.NTyx; ++k) {
214  for (i = 0; i < theCurrentTemp.head.NTxx; ++i) {
215  in_file >> theCurrentTemp.entx[k][i].runnum >> costrk[0] >> costrk[1] >> costrk[2];
216 
217  if (in_file.fail()) {
218  LOGERROR("SiPixelGenError") << "Error reading file 17, no GenError load, run # "
219  << theCurrentTemp.entx[k][i].runnum << ENDL;
220  return false;
221  }
222 
223  // Calculate the alpha, beta, and cot(beta) for this entry
224 
225  theCurrentTemp.entx[k][i].cotalpha = costrk[0] / costrk[2];
226 
227  theCurrentTemp.entx[k][i].cotbeta = costrk[1] / costrk[2];
228 
229  in_file >> theCurrentTemp.entx[k][i].qavg >> theCurrentTemp.entx[k][i].pixmax >>
230  theCurrentTemp.entx[k][i].dyone >> theCurrentTemp.entx[k][i].syone >> theCurrentTemp.entx[k][i].dxone >>
231  theCurrentTemp.entx[k][i].sxone;
232 
233  if (in_file.fail()) {
234  LOGERROR("SiPixelGenError") << "Error reading file 18, no GenError load, run # "
235  << theCurrentTemp.entx[k][i].runnum << ENDL;
236  return false;
237  }
238 
239  in_file >> theCurrentTemp.entx[k][i].dytwo >> theCurrentTemp.entx[k][i].sytwo >>
240  theCurrentTemp.entx[k][i].dxtwo >> theCurrentTemp.entx[k][i].sxtwo >> theCurrentTemp.entx[k][i].qmin >>
241  theCurrentTemp.entx[k][i].qmin2;
242  // >> theCurrentTemp.entx[k][i].mpvvav >> theCurrentTemp.entx[k][i].sigmavav >> theCurrentTemp.entx[k][i].kappavav;
243 
244  if (in_file.fail()) {
245  LOGERROR("SiPixelGenError") << "Error reading file 19, no GenError load, run # "
246  << theCurrentTemp.entx[k][i].runnum << ENDL;
247  return false;
248  }
249 
250  for (j = 0; j < 4; ++j) {
251  in_file >> theCurrentTemp.entx[k][i].yavggen[j] >> theCurrentTemp.entx[k][i].yrmsgen[j] >>
252  theCurrentTemp.entx[k][i].xavggen[j] >> theCurrentTemp.entx[k][i].xrmsgen[j];
253 
254  if (in_file.fail()) {
255  LOGERROR("SiPixelGenError") << "Error reading file 30a, no GenError load, run # "
256  << theCurrentTemp.entx[k][i].runnum << ENDL;
257  return false;
258  }
259  }
260  }
261  }
262 
263  in_file.close();
264 
265  // Add this info to the store
266 
267  pixelTemp.push_back(theCurrentTemp);
268 
269  postInit(pixelTemp);
270 
271  return true;
272 
273  } else {
274  // If file didn't open, report this
275 
276  LOGERROR("SiPixelGenError") << "Error opening File" << tempfile << ENDL;
277  return false;
278  }
279 
280 } // TempInit
281 
282 #ifndef SI_PIXEL_TEMPLATE_STANDALONE
283 
284 //****************************************************************
288 //****************************************************************
289 bool SiPixelGenError::pushfile(const SiPixelGenErrorDBObject& dbobject, std::vector<SiPixelGenErrorStore>& pixelTemp) {
290  // Add GenError stored in external dbobject to theGenErrorStore
291 
292  // Local variables
293  int i, j, k;
294  float costrk[3] = {0, 0, 0};
295  // const char *tempfile;
296  const int code_version = {1};
297 
298  // We must create a new object because dbobject must be a const and our stream must not be
299  SiPixelGenErrorDBObject db = dbobject;
300 
301  // Create a local GenError storage entry
303  auto tmpPtr = std::make_unique<SiPixelGenErrorStore>(); // must be allocated on the heap instead
304  auto& theCurrentTemp = *tmpPtr;
305 
306  // Fill the GenError storage for each GenError calibration stored in the db
307  for (int m = 0; m < db.numOfTempl(); ++m) {
308  // Read-in a header string first and print it
309 
311  for (i = 0; i < 20; ++i) {
312  temp.f = db.sVector()[db.index()];
313  theCurrentTemp.head.title[4 * i] = temp.c[0];
314  theCurrentTemp.head.title[4 * i + 1] = temp.c[1];
315  theCurrentTemp.head.title[4 * i + 2] = temp.c[2];
316  theCurrentTemp.head.title[4 * i + 3] = temp.c[3];
317  db.incrementIndex(1);
318  }
319 
320  theCurrentTemp.head.title[79] = '\0';
321  LOGINFO("SiPixelGenError") << "Loading Pixel GenError File - " << theCurrentTemp.head.title << ENDL;
322 
323  // next, the header information
324 
325  db >> theCurrentTemp.head.ID >> theCurrentTemp.head.templ_version >> theCurrentTemp.head.Bfield >>
326  theCurrentTemp.head.NTy >> theCurrentTemp.head.NTyx >> theCurrentTemp.head.NTxx >> theCurrentTemp.head.Dtype >>
327  theCurrentTemp.head.Vbias >> theCurrentTemp.head.temperature >> theCurrentTemp.head.fluence >>
328  theCurrentTemp.head.qscale >> theCurrentTemp.head.s50 >> theCurrentTemp.head.lorywidth >>
329  theCurrentTemp.head.lorxwidth >> theCurrentTemp.head.ysize >> theCurrentTemp.head.xsize >>
330  theCurrentTemp.head.zsize >> theCurrentTemp.head.ss50 >> theCurrentTemp.head.lorybias >>
331  theCurrentTemp.head.lorxbias >> theCurrentTemp.head.fbin[0] >> theCurrentTemp.head.fbin[1] >>
332  theCurrentTemp.head.fbin[2];
333 
334  if (db.fail()) {
335  LOGERROR("SiPixelGenError") << "Error reading file, no GenError load" << ENDL;
336  return false;
337  }
338 
339  LOGINFO("SiPixelGenError") << "GenError ID = " << theCurrentTemp.head.ID << ", GenError Version "
340  << theCurrentTemp.head.templ_version << ", Bfield = " << theCurrentTemp.head.Bfield
341  << ", NTy = " << theCurrentTemp.head.NTy << ", NTyx = " << theCurrentTemp.head.NTyx
342  << ", NTxx = " << theCurrentTemp.head.NTxx << ", Dtype = " << theCurrentTemp.head.Dtype
343  << ", Bias voltage " << theCurrentTemp.head.Vbias << ", temperature "
344  << theCurrentTemp.head.temperature << ", fluence " << theCurrentTemp.head.fluence
345  << ", Q-scaling factor " << theCurrentTemp.head.qscale << ", 1/2 multi dcol threshold "
346  << theCurrentTemp.head.s50 << ", 1/2 single dcol threshold " << theCurrentTemp.head.ss50
347  << ", y Lorentz Width " << theCurrentTemp.head.lorywidth << ", y Lorentz Bias "
348  << theCurrentTemp.head.lorybias << ", x Lorentz width " << theCurrentTemp.head.lorxwidth
349  << ", x Lorentz Bias " << theCurrentTemp.head.lorxbias
350  << ", Q/Q_avg fractions for Qbin defs " << theCurrentTemp.head.fbin[0] << ", "
351  << theCurrentTemp.head.fbin[1] << ", " << theCurrentTemp.head.fbin[2]
352  << ", pixel x-size " << theCurrentTemp.head.xsize << ", y-size "
353  << theCurrentTemp.head.ysize << ", zsize " << theCurrentTemp.head.zsize << ENDL;
354 
355  LOGINFO("SiPixelGenError") << "Loading Pixel GenError - " << theCurrentTemp.head.title << " version "
356  << theCurrentTemp.head.templ_version << " code v." << code_version << ENDL;
357  if (theCurrentTemp.head.templ_version < code_version) {
358  LOGERROR("SiPixelGenError") << "code expects version " << code_version << ", no GenError load" << ENDL;
359  return false;
360  }
361 
362 #ifdef SI_PIXEL_TEMPLATE_USE_BOOST
363 
364  // next, layout the 1-d/2-d structures needed to store GenError
365 
366  // &&& Who is going to delete these? Are we leaking memory?
367  theCurrentTemp.cotbetaY = new float[theCurrentTemp.head.NTy];
368  theCurrentTemp.cotbetaX = new float[theCurrentTemp.head.NTyx];
369  theCurrentTemp.cotalphaX = new float[theCurrentTemp.head.NTxx];
370 
371  theCurrentTemp.enty.resize(boost::extents[theCurrentTemp.head.NTy]);
372 
373  theCurrentTemp.entx.resize(boost::extents[theCurrentTemp.head.NTyx][theCurrentTemp.head.NTxx]);
374 
375 #endif
376 
377  // next, loop over all barrel y-angle entries
378 
379  for (i = 0; i < theCurrentTemp.head.NTy; ++i) {
380  db >> theCurrentTemp.enty[i].runnum >> costrk[0] >> costrk[1] >> costrk[2];
381 
382  if (db.fail()) {
383  LOGERROR("SiPixelGenError") << "Error reading file 1, no GenError load, run # " << theCurrentTemp.enty[i].runnum
384  << ENDL;
385  return false;
386  }
387 
388  // Calculate the alpha, beta, and cot(beta) for this entry
389 
390  theCurrentTemp.enty[i].cotalpha = costrk[0] / costrk[2];
391 
392  theCurrentTemp.enty[i].cotbeta = costrk[1] / costrk[2];
393 
394  db >> theCurrentTemp.enty[i].qavg >> theCurrentTemp.enty[i].pixmax >> theCurrentTemp.enty[i].dyone >>
395  theCurrentTemp.enty[i].syone >> theCurrentTemp.enty[i].dxone >> theCurrentTemp.enty[i].sxone;
396 
397  if (db.fail()) {
398  LOGERROR("SiPixelGenError") << "Error reading file 2, no GenError load, run # " << theCurrentTemp.enty[i].runnum
399  << ENDL;
400  return false;
401  }
402 
403  db >> theCurrentTemp.enty[i].dytwo >> theCurrentTemp.enty[i].sytwo >> theCurrentTemp.enty[i].dxtwo >>
404  theCurrentTemp.enty[i].sxtwo >> theCurrentTemp.enty[i].qmin >> theCurrentTemp.enty[i].qmin2;
405 
406  for (j = 0; j < 4; ++j) {
407  db >> theCurrentTemp.enty[i].yavggen[j] >> theCurrentTemp.enty[i].yrmsgen[j] >>
408  theCurrentTemp.enty[i].xavggen[j] >> theCurrentTemp.enty[i].xrmsgen[j];
409 
410  if (db.fail()) {
411  LOGERROR("SiPixelGenError") << "Error reading file 14a, no GenError load, run # "
412  << theCurrentTemp.enty[i].runnum << ENDL;
413  return false;
414  }
415  }
416  }
417 
418  // next, loop over all barrel x-angle entries
419 
420  for (k = 0; k < theCurrentTemp.head.NTyx; ++k) {
421  for (i = 0; i < theCurrentTemp.head.NTxx; ++i) {
422  db >> theCurrentTemp.entx[k][i].runnum >> costrk[0] >> costrk[1] >> costrk[2];
423 
424  if (db.fail()) {
425  LOGERROR("SiPixelGenError") << "Error reading file 17, no GenError load, run # "
426  << theCurrentTemp.entx[k][i].runnum << ENDL;
427  return false;
428  }
429 
430  // Calculate the alpha, beta, and cot(beta) for this entry
431 
432  theCurrentTemp.entx[k][i].cotalpha = costrk[0] / costrk[2];
433 
434  theCurrentTemp.entx[k][i].cotbeta = costrk[1] / costrk[2];
435 
436  db >> theCurrentTemp.entx[k][i].qavg >> theCurrentTemp.entx[k][i].pixmax >> theCurrentTemp.entx[k][i].dyone >>
437  theCurrentTemp.entx[k][i].syone >> theCurrentTemp.entx[k][i].dxone >> theCurrentTemp.entx[k][i].sxone;
438 
439  if (db.fail()) {
440  LOGERROR("SiPixelGenError") << "Error reading file 18, no GenError load, run # "
441  << theCurrentTemp.entx[k][i].runnum << ENDL;
442  return false;
443  }
444 
445  db >> theCurrentTemp.entx[k][i].dytwo >> theCurrentTemp.entx[k][i].sytwo >> theCurrentTemp.entx[k][i].dxtwo >>
446  theCurrentTemp.entx[k][i].sxtwo >> theCurrentTemp.entx[k][i].qmin >> theCurrentTemp.entx[k][i].qmin2;
447 
448  for (j = 0; j < 4; ++j) {
449  db >> theCurrentTemp.entx[k][i].yavggen[j] >> theCurrentTemp.entx[k][i].yrmsgen[j] >>
450  theCurrentTemp.entx[k][i].xavggen[j] >> theCurrentTemp.entx[k][i].xrmsgen[j];
451 
452  if (db.fail()) {
453  LOGERROR("SiPixelGenError") << "Error reading file 30a, no GenError load, run # "
454  << theCurrentTemp.entx[k][i].runnum << ENDL;
455  return false;
456  }
457  }
458  }
459  }
460 
461  // Add this GenError to the store
462 
463  pixelTemp.push_back(theCurrentTemp);
464 
465  postInit(pixelTemp);
466  }
467  return true;
468 
469 } // TempInit
470 
471 #endif
472 
473 void SiPixelGenError::postInit(std::vector<SiPixelGenErrorStore>& thePixelTemp_) {
474  for (auto& templ : thePixelTemp_) {
475  for (auto iy = 0; iy < templ.head.NTy; ++iy)
476  templ.cotbetaY[iy] = templ.enty[iy].cotbeta;
477  for (auto iy = 0; iy < templ.head.NTyx; ++iy)
478  templ.cotbetaX[iy] = templ.entx[iy][0].cotbeta;
479  for (auto ix = 0; ix < templ.head.NTxx; ++ix)
480  templ.cotalphaX[ix] = templ.entx[0][ix].cotalpha;
481  }
482 }
483 
484 // ************************************************************************************************************
506 // ************************************************************************************************************
507 // a simpler method just to return the LA
509  // Find the index corresponding to id
510 
511  if (id != id_current_) {
512  index_id_ = -1;
513  for (int i = 0; i < (int)thePixelTemp_.size(); ++i) {
514  if (id == thePixelTemp_[i].head.ID) {
515  index_id_ = i;
516  id_current_ = id;
517  //
518  lorywidth_ = thePixelTemp_[i].head.lorywidth;
519  lorxwidth_ = thePixelTemp_[i].head.lorxwidth;
520  lorybias_ = thePixelTemp_[i].head.lorybias;
521  lorxbias_ = thePixelTemp_[i].head.lorxbias;
522 
523  //for(int j=0; j<3; ++j) {fbin_[j] = thePixelTemp_[i].head.fbin[j];}
524 
525  // Pixel sizes to the private variables
526  xsize_ = thePixelTemp_[i].head.xsize;
527  ysize_ = thePixelTemp_[i].head.ysize;
528  zsize_ = thePixelTemp_[i].head.zsize;
529 
530  break;
531  }
532  }
533  }
534  return index_id_;
535 }
536 //-----------------------------------------------------------------------
537 // Full method
539  float cotalpha,
540  float cotbeta,
541  float locBz,
542  float locBx,
543  float qclus,
544  bool irradiationCorrections,
545  int& pixmx,
546  float& sigmay,
547  float& deltay,
548  float& sigmax,
549  float& deltax,
550  float& sy1,
551  float& dy1,
552  float& sy2,
553  float& dy2,
554  float& sx1,
555  float& dx1,
556  float& sx2,
557  float& dx2) {
558  // Interpolate for a new set of track angles
559 
560  // Find the index corresponding to id
561 
562  if (id != id_current_) {
563  index_id_ = -1;
564  for (int i = 0; i < (int)thePixelTemp_.size(); ++i) {
565  if (id == thePixelTemp_[i].head.ID) {
566  index_id_ = i;
567  id_current_ = id;
568  lorywidth_ = thePixelTemp_[i].head.lorywidth;
569  lorxwidth_ = thePixelTemp_[i].head.lorxwidth;
570  lorybias_ = thePixelTemp_[i].head.lorybias;
571  lorxbias_ = thePixelTemp_[i].head.lorxbias;
572  for (int j = 0; j < 3; ++j) {
573  fbin_[j] = thePixelTemp_[i].head.fbin[j];
574  }
575 
576  // Pixel sizes to the private variables
577 
578  xsize_ = thePixelTemp_[i].head.xsize;
579  ysize_ = thePixelTemp_[i].head.ysize;
580  zsize_ = thePixelTemp_[i].head.zsize;
581 
582  break;
583  }
584  }
585  }
586 
587  int index = index_id_;
588 
589 #ifndef SI_PIXEL_TEMPLATE_STANDALONE
590  if (index < 0 || index >= (int)thePixelTemp_.size()) {
591  throw cms::Exception("DataCorrupt") << "SiPixelGenError::qbin can't find needed GenError ID = " << id << std::endl;
592  }
593 #else
594  assert(index >= 0 && index < (int)thePixelTemp_.size());
595 #endif
596 
597  //
598 
599  auto const& templ = thePixelTemp_[index];
600 
601  // Interpolate the absolute value of cot(beta)
602 
603  auto acotb = std::abs(cotbeta);
604 
605  // qcorrect corrects the cot(alpha)=0 cluster charge for non-zero cot(alpha)
606 
607  auto cotalpha0 = thePixelTemp_[index].enty[0].cotalpha;
608  auto qcorrect =
609  std::sqrt((1.f + cotbeta * cotbeta + cotalpha * cotalpha) / (1.f + cotbeta * cotbeta + cotalpha0 * cotalpha0));
610 
611  // for some cosmics, the ususal gymnastics are incorrect
612 
613  float cota = cotalpha;
614  float cotb = acotb;
615  bool flip_y;
616  bool flip_x;
617  // for some cosmics, the ususal gymnastics are incorrect
618  flip_x = false;
619  flip_y = false;
620  switch (thePixelTemp_[index_id_].head.Dtype) {
621  case 0:
622  if (cotbeta < 0.f) {
623  flip_y = true;
624  }
625  break;
626  case 1:
627  if (locBz < 0.f) {
628  cotb = cotbeta;
629  } else {
630  cotb = -cotbeta;
631  flip_y = true;
632  }
633  break;
634  case 2:
635  case 3:
636  case 4:
637  case 5:
638  if (locBx * locBz < 0.f) {
639  cota = -cotalpha;
640  flip_x = true;
641  }
642  if (locBx > 0.f) {
643  cotb = cotbeta;
644  } else {
645  cotb = -cotbeta;
646  flip_y = true;
647  }
648  break;
649  default:
650 #ifndef SI_PIXEL_TEMPLATE_STANDALONE
651  throw cms::Exception("DataCorrupt")
652  << "SiPixelGenError::illegal subdetector ID = " << thePixelTemp_[index_id_].head.Dtype << std::endl;
653 #else
654  std::cout << "SiPixelGenError::illegal subdetector ID = " << thePixelTemp_[index_id_].head.Dtype << std::endl;
655 #endif
656  }
657 
658  // Copy the charge scaling factor to the private variable
659 
660  if (flip_y) {
661  lorybias_ = -lorybias_;
662  lorywidth_ = -lorywidth_;
663  }
664  if (flip_x) {
665  lorxbias_ = -lorxbias_;
666  lorxwidth_ = -lorxwidth_;
667  }
668 
669  auto qscale = thePixelTemp_[index].head.qscale;
670 
671  /*
672  lorywidth = thePixelTemp_[index].head.lorywidth;
673  if(locBz > 0.f) {lorywidth = -lorywidth;}
674  lorxwidth = thePixelTemp_[index].head.lorxwidth;
675  */
676 
677  auto Ny = thePixelTemp_[index].head.NTy;
678  auto Nyx = thePixelTemp_[index].head.NTyx;
679  auto Nxx = thePixelTemp_[index].head.NTxx;
680 
681 #ifndef SI_PIXEL_TEMPLATE_STANDALONE
682  if (Ny < 2 || Nyx < 1 || Nxx < 2) {
683  throw cms::Exception("DataCorrupt") << "GenError ID = " << id_current_ << "has too few entries: Ny/Nyx/Nxx = " << Ny
684  << "/" << Nyx << "/" << Nxx << std::endl;
685  }
686 #else
687  assert(Ny > 1 && Nyx > 0 && Nxx > 1);
688 #endif
689 
690  // next, loop over all y-angle entries
691 
692  auto ilow = 0;
693  auto ihigh = 0;
694  auto yratio = 0.f;
695 
696  {
697  auto j = std::lower_bound(templ.cotbetaY, templ.cotbetaY + Ny, cotb);
698  if (j == templ.cotbetaY + Ny) {
699  --j;
700  yratio = 1.f;
701  } else if (j == templ.cotbetaY) {
702  ++j;
703  yratio = 0.f;
704  } else {
705  yratio = (cotb - (*(j - 1))) / ((*j) - (*(j - 1)));
706  }
707 
708  ihigh = j - templ.cotbetaY;
709  ilow = ihigh - 1;
710  }
711 
712  // Interpolate/store all y-related quantities (flip displacements when flip_y)
713 
714  auto qavg = (1.f - yratio) * thePixelTemp_[index].enty[ilow].qavg + yratio * thePixelTemp_[index].enty[ihigh].qavg;
715  qavg *= qcorrect;
716  auto qmin = (1.f - yratio) * thePixelTemp_[index].enty[ilow].qmin + yratio * thePixelTemp_[index].enty[ihigh].qmin;
717  qmin *= qcorrect;
718  auto qmin2 = (1.f - yratio) * thePixelTemp_[index].enty[ilow].qmin2 + yratio * thePixelTemp_[index].enty[ihigh].qmin2;
719  qmin2 *= qcorrect;
720 
721 #ifndef SI_PIXEL_TEMPLATE_STANDALONE
722  if (qavg <= 0.f || qmin <= 0.f) {
723  throw cms::Exception("DataCorrupt")
724  << "SiPixelGenError::qbin, qavg or qmin <= 0,"
725  << " Probably someone called the generic pixel reconstruction with an illegal trajectory state" << std::endl;
726  }
727 #else
728  assert(qavg > 0.f && qmin > 0.f);
729 #endif
730 
731  // Scale the input charge to account for differences between pixelav and CMSSW simulation or data
732 
733  auto qtotal = qscale * qclus;
734 
735  // uncertainty and final corrections depend upon total charge bin
736 
737  auto fq = qtotal / qavg;
738  int binq;
739  if (fq > fbin_[0]) {
740  binq = 0;
741  } else {
742  if (fq > fbin_[1]) {
743  binq = 1;
744  } else {
745  if (fq > fbin_[2]) {
746  binq = 2;
747  } else {
748  binq = 3;
749  }
750  }
751  }
752 
753  auto yrmsgen = (1.f - yratio) * thePixelTemp_[index].enty[ilow].yrmsgen[binq] +
754  yratio * thePixelTemp_[index].enty[ihigh].yrmsgen[binq];
755  sy1 = (1.f - yratio) * thePixelTemp_[index].enty[ilow].syone + yratio * thePixelTemp_[index].enty[ihigh].syone;
756  sy2 = (1.f - yratio) * thePixelTemp_[index].enty[ilow].sytwo + yratio * thePixelTemp_[index].enty[ihigh].sytwo;
757 
758  if (irradiationCorrections) {
759  auto yavggen = (1.f - yratio) * thePixelTemp_[index].enty[ilow].yavggen[binq] +
760  yratio * thePixelTemp_[index].enty[ihigh].yavggen[binq];
761  if (flip_y) {
762  yavggen = -yavggen;
763  }
764  deltay = yavggen;
765  dy1 = (1.f - yratio) * thePixelTemp_[index].enty[ilow].dyone + yratio * thePixelTemp_[index].enty[ihigh].dyone;
766  if (flip_y) {
767  dy1 = -dy1;
768  }
769  dy2 = (1.f - yratio) * thePixelTemp_[index].enty[ilow].dytwo + yratio * thePixelTemp_[index].enty[ihigh].dytwo;
770  if (flip_y) {
771  dy2 = -dy2;
772  }
773  }
774 
775  // next, loop over all x-angle entries, first, find relevant y-slices
776 
777  auto iylow = 0;
778  auto iyhigh = 0;
779  auto yxratio = 0.f;
780 
781  {
782  auto j = std::lower_bound(templ.cotbetaX, templ.cotbetaX + Nyx, acotb);
783  if (j == templ.cotbetaX + Nyx) {
784  --j;
785  yxratio = 1.f;
786  } else if (j == templ.cotbetaX) {
787  ++j;
788  yxratio = 0.f;
789  } else {
790  yxratio = (acotb - (*(j - 1))) / ((*j) - (*(j - 1)));
791  }
792 
793  iyhigh = j - templ.cotbetaX;
794  iylow = iyhigh - 1;
795  }
796 
797  auto xxratio = 0.f;
798 
799  {
800  auto j = std::lower_bound(templ.cotalphaX, templ.cotalphaX + Nxx, cota);
801  if (j == templ.cotalphaX + Nxx) {
802  --j;
803  xxratio = 1.f;
804  } else if (j == templ.cotalphaX) {
805  ++j;
806  xxratio = 0.f;
807  } else {
808  xxratio = (cota - (*(j - 1))) / ((*j) - (*(j - 1)));
809  }
810 
811  ihigh = j - templ.cotalphaX;
812  ilow = ihigh - 1;
813  }
814 
815  sx1 =
816  (1.f - xxratio) * thePixelTemp_[index].entx[0][ilow].sxone + xxratio * thePixelTemp_[index].entx[0][ihigh].sxone;
817  sx2 =
818  (1.f - xxratio) * thePixelTemp_[index].entx[0][ilow].sxtwo + xxratio * thePixelTemp_[index].entx[0][ihigh].sxtwo;
819 
820  // pixmax is the maximum allowed pixel charge (used for truncation)
821 
822  pixmx = (1.f - yxratio) * ((1.f - xxratio) * thePixelTemp_[index].entx[iylow][ilow].pixmax +
823  xxratio * thePixelTemp_[index].entx[iylow][ihigh].pixmax) +
824  yxratio * ((1.f - xxratio) * thePixelTemp_[index].entx[iyhigh][ilow].pixmax +
825  xxratio * thePixelTemp_[index].entx[iyhigh][ihigh].pixmax);
826 
827  auto xrmsgen = (1.f - yxratio) * ((1.f - xxratio) * thePixelTemp_[index].entx[iylow][ilow].xrmsgen[binq] +
828  xxratio * thePixelTemp_[index].entx[iylow][ihigh].xrmsgen[binq]) +
829  yxratio * ((1.f - xxratio) * thePixelTemp_[index].entx[iyhigh][ilow].xrmsgen[binq] +
830  xxratio * thePixelTemp_[index].entx[iyhigh][ihigh].xrmsgen[binq]);
831 
832  if (irradiationCorrections) {
833  auto xavggen = (1.f - yxratio) * ((1.f - xxratio) * thePixelTemp_[index].entx[iylow][ilow].xavggen[binq] +
834  xxratio * thePixelTemp_[index].entx[iylow][ihigh].xavggen[binq]) +
835  yxratio * ((1.f - xxratio) * thePixelTemp_[index].entx[iyhigh][ilow].xavggen[binq] +
836  xxratio * thePixelTemp_[index].entx[iyhigh][ihigh].xavggen[binq]);
837  if (flip_x) {
838  xavggen = -xavggen;
839  }
840  deltax = xavggen;
841  dx1 = (1.f - xxratio) * thePixelTemp_[index].entx[0][ilow].dxone +
842  xxratio * thePixelTemp_[index].entx[0][ihigh].dxone;
843  if (flip_x) {
844  dx1 = -dx1;
845  }
846  dx2 = (1.f - xxratio) * thePixelTemp_[index].entx[0][ilow].dxtwo +
847  xxratio * thePixelTemp_[index].entx[0][ihigh].dxtwo;
848  if (flip_x) {
849  dx2 = -dx2;
850  }
851  }
852 
853  // Take the errors and bias from the correct charge bin
854 
855  sigmay = yrmsgen;
856 
857  sigmax = xrmsgen;
858 
859  // If the charge is too small (then flag it)
860 
861  if (qtotal < 0.95f * qmin) {
862  binq = 5;
863  } else {
864  if (qtotal < 0.95f * qmin2) {
865  binq = 4;
866  }
867  }
868 
869  return binq;
870 
871 } // qbin
872 
874  float cotalpha,
875  float cotbeta,
876  float locBz,
877  float locBx,
878  float qclus,
879  float& pixmx,
880  float& sigmay,
881  float& deltay,
882  float& sigmax,
883  float& deltax,
884  float& sy1,
885  float& dy1,
886  float& sy2,
887  float& dy2,
888  float& sx1,
889  float& dx1,
890  float& sx2,
891  float& dx2) {
892  // Interpolate for a new set of track angles
893 
894  bool irradiationCorrections = true;
895  int ipixmx, ibin;
896 
897  ibin = SiPixelGenError::qbin(id,
898  cotalpha,
899  cotbeta,
900  locBz,
901  locBx,
902  qclus,
903  irradiationCorrections,
904  ipixmx,
905  sigmay,
906  deltay,
907  sigmax,
908  deltax,
909  sy1,
910  dy1,
911  sy2,
912  dy2,
913  sx1,
914  dx1,
915  sx2,
916  dx2);
917 
918  pixmx = (float)ipixmx;
919 
920  return ibin;
921 }
SiPixelGenErrorEntry enty[100]
60 x templates spanning cluster lengths from -6px (-1.125Rad) to +6px (+1.125Rad) in each of 60 slice...
float qavg
average cluster charge for this set of track angles (now includes threshold effects) ...
float ss50
1/2 of the single hit dcol threshold in electrons
float qmin
minimum cluster charge for valid hit (keeps 99.9% of simulated hits)
float Bfield
Bfield in Tesla.
int runnum
< Basic template entry corresponding to a single set of track angles
float yrmsgen[4]
generic algorithm: average y-rms of reconstruction binned in 4 charge bins
float dxone
mean offset/correction for one pixel x-clusters
static bool pushfile(int filenum, std::vector< SiPixelGenErrorStore > &pixelTemp, std::string dir="")
#define LOGINFO(x)
for(int i=first, nt=offsets[nh];i< nt;i+=gridDim.x *blockDim.x)
float Vbias
detector bias potential in Volts
float xrmsgen[4]
generic algorithm: average x-rms of reconstruction binned in 4 charge bins
int NTxx
number of Template x-entries in each slice
float fbin[3]
The QBin definitions in Q_clus/Q_avg.
float syone
rms for one pixel y-clusters
float zsize
pixel size (for future use in upgraded geometry)
assert(be >=bs)
float s50
1/2 of the multihit dcol threshold in electrons
float cotalpha
cot(alpha) is proportional to cluster length in x and is basis of interpolation
float lorxbias
estimate of x-lorentz bias
float temperature
detector temperature in deg K
int qbin(int id, float cotalpha, float cotbeta, float locBz, float locBx, float qclus, bool irradiationCorrections, int &pixmx, float &sigmay, float &deltay, float &sigmax, float &deltax, float &sy1, float &dy1, float &sy2, float &dy2, float &sx1, float &dx1, float &sx2, float &dx2)
float xsize
pixel size (for future use in upgraded geometry)
static void postInit(std::vector< SiPixelGenErrorStore > &thePixelTemp_)
int templ_version
Version number of the template to ensure code compatibility.
float cotbeta
cot(beta) is proportional to cluster length in y and is basis of interpolation
T sqrt(T t)
Definition: SSEVec.h:19
int ID
< template header structure
float sxone
rms for one pixel x-clusters
Abs< T >::type abs(const T &t)
Definition: Abs.h:22
float fluence
radiation fluence in n_eq/cm^2
#define LOGERROR(x)
double f[11][100]
float dytwo
mean offset/correction for one double-pixel y-clusters
int NTy
number of Template y entries
float qscale
Charge scaling to match cmssw and pixelav.
float dxtwo
mean offset/correction for one double-pixel x-clusters
SiPixelGenErrorHeader head
< template storage structure
float ysize
pixel size (for future use in upgraded geometry)
char title[80]
template title
float sytwo
rms for one double-pixel y-clusters
float lorywidth
estimate of y-lorentz width for optimal resolution
float cotalphaX[80]
60 y templates spanning cluster lengths from 0px to +18px
#define ENDL
float yavggen[4]
generic algorithm: average y-bias of reconstruction binned in 4 charge bins
float dyone
mean offset/correction for one pixel y-clusters
HLT enums.
int Dtype
detector type (0=BPix, 1=FPix)
int NTyx
number of Template y-slices of x entries
SiPixelGenErrorEntry entx[80][80]
float xavggen[4]
generic algorithm: average x-bias of reconstruction binned in 4 charge bins
float pixmax
maximum charge for individual pixels in cluster
float sxtwo
rms for one double-pixel x-clusters
float lorybias
estimate of y-lorentz bias
float lorxwidth
estimate of x-lorentz width for optimal resolution