CMS 3D CMS Logo

CSCGEMMotherboard.cc
Go to the documentation of this file.
2 
4  unsigned sector, unsigned subsector,
5  unsigned chamber,
6  const edm::ParameterSet& conf) :
7  CSCUpgradeMotherboard(endcap, station, sector, subsector, chamber, conf)
8  , maxDeltaBXPad_(tmbParams_.getParameter<int>("maxDeltaBXPad"))
9  , maxDeltaBXCoPad_(tmbParams_.getParameter<int>("maxDeltaBXCoPad"))
10  , useOldLCTDataFormat_(tmbParams_.getParameter<bool>("useOldLCTDataFormat"))
11  , promoteALCTGEMpattern_(tmbParams_.getParameter<bool>("promoteALCTGEMpattern"))
12  , promoteALCTGEMquality_(tmbParams_.getParameter<bool>("promoteALCTGEMquality"))
13  , doLCTGhostBustingWithGEMs_(tmbParams_.getParameter<bool>("doLCTGhostBustingWithGEMs"))
14 {
15  // super chamber has layer=0!
17 
18  const edm::ParameterSet coPadParams(station==1 ?
19  conf.getParameter<edm::ParameterSet>("copadParamGE11") :
20  conf.getParameter<edm::ParameterSet>("copadParamGE21"));
21  coPadProcessor.reset( new GEMCoPadProcessor(endcap, station, chamber, coPadParams) );
22 
23  maxDeltaPadL1_ = (theParity ? tmbParams_.getParameter<int>("maxDeltaPadL1Even") :
24  tmbParams_.getParameter<int>("maxDeltaPadL1Odd") );
25  maxDeltaPadL2_ = (theParity ? tmbParams_.getParameter<int>("maxDeltaPadL2Even") :
26  tmbParams_.getParameter<int>("maxDeltaPadL2Odd") );
27 }
28 
31 {
32 }
33 
35 {
36 }
37 
39 {
41  pads_.clear();
42  coPads_.clear();
43 }
44 
45 
47  const CSCComparatorDigiCollection* compdc,
48  const GEMPadDigiClusterCollection* gemClusters)
49 {
50  std::unique_ptr<GEMPadDigiCollection> gemPads(new GEMPadDigiCollection());
51  coPadProcessor->declusterize(gemClusters, *gemPads);
52  run(wiredc, compdc, gemPads.get());
53 }
54 
55 
57 {
58  pads_.clear();
59  auto superChamber(gem_g->superChamber(id));
60  for (const auto& ch : superChamber->chambers()) {
61  for (const auto& roll : ch->etaPartitions()) {
62  GEMDetId roll_id(roll->id());
63  auto pads_in_det = gemPads->get(roll_id);
64  for (auto pad = pads_in_det.first; pad != pads_in_det.second; ++pad) {
65  const int bx_shifted(CSCConstants::LCT_CENTRAL_BX + pad->bx());
66  // consider matches with BX difference +1/0/-1
67  for (int bx = bx_shifted - maxDeltaBXPad_;bx <= bx_shifted + maxDeltaBXPad_; ++bx) {
68  pads_[bx].emplace_back(roll_id.rawId(), *pad);
69  }
70  }
71  }
72  }
73 }
74 
76 {
77  coPads_.clear();
78  for (const auto& copad: gemCoPadV){
79  GEMDetId detId(theRegion, 1, theStation, 0, theChamber, 0);
80  // only consider matches with same BX
81  coPads_[CSCConstants::LCT_CENTRAL_BX + copad.bx(1)].emplace_back(detId.rawId(), copad);
82  }
83 }
84 
86  const GEMCoPadDigi& gem,
87  int trknmb) const
88 {
89  return constructLCTsGEM(alct, CSCCLCTDigi(), GEMPadDigi(), gem, trknmb);
90 }
91 
92 
94  const GEMCoPadDigi& gem,
95  int trknmb) const
96 {
97  return constructLCTsGEM(CSCALCTDigi(), clct, GEMPadDigi(), gem, trknmb);
98 }
99 
101  const CSCCLCTDigi& clct,
102  const GEMCoPadDigi& gem,
103  int trknmb) const
104 {
105  return constructLCTsGEM(alct, clct, GEMPadDigi(), gem, trknmb);
106 }
107 
108 
110  const CSCCLCTDigi& clct,
111  const GEMPadDigi& gem,
112  int trknmb) const
113 {
114  return constructLCTsGEM(alct, clct, gem, GEMCoPadDigi(), trknmb);
115 }
116 
118  const CSCCLCTDigi& clct,
119  const GEMPadDigi& gem1,
120  const GEMCoPadDigi& gem2,
121  int trknmb) const
122 {
123  int pattern = 0, quality = 0, bx = 0, keyStrip = 0, keyWG = 0, bend = 0, valid = 0;
124 
125  // make a new LCT
126  CSCCorrelatedLCTDigi thisLCT;
127  if (not alct.isValid() and not clct.isValid()) {
128  LogTrace("CSCGEMCMotherboard") << "Warning!!! either ALCT or CLCT not valid, return invalid LCT \n";
129  return thisLCT;
130  }
131 
132  // Determine the case and assign properties depending on the LCT dataformat (old/new)
133  if (alct.isValid() and clct.isValid() and gem1.isValid() and not gem2.isValid()) {
134  pattern = encodePattern(clct.getPattern());
135  quality = findQualityGEM(alct, clct, 1);
136  bx = alct.getBX();
137  keyStrip = clct.getKeyStrip();
138  keyWG = alct.getKeyWG();
139  bend = clct.getBend();
140  thisLCT.setALCT(getBXShiftedALCT(alct));
141  thisLCT.setCLCT(clct);
142  thisLCT.setGEM1(gem1);
144  }
145  else if (alct.isValid() and clct.isValid() and not gem1.isValid() and gem2.isValid()) {
146  pattern = encodePattern(clct.getPattern());
147  quality = findQualityGEM(alct, clct, 2);
148  bx = alct.getBX();
149  keyStrip = clct.getKeyStrip();
150  keyWG = alct.getKeyWG();
151  bend = clct.getBend();
152  thisLCT.setALCT(getBXShiftedALCT(alct));
153  thisLCT.setCLCT(clct);
154  thisLCT.setGEM1(gem2.first());
155  thisLCT.setGEM2(gem2.second());
157  }
158  else if (alct.isValid() and gem2.isValid() and not clct.isValid()) {
159  //in ME11
160  //ME1b: keyWG >15,
161  //ME1a and ME1b overlap: 10<=keyWG<=15
162  //ME1a: keyWG < 10
163  //in overlap region, firstly try a match in ME1b
164 
165  auto p(getCSCPart(-1));//use -1 as fake halfstrip, it returns ME11 if station==1 && (ring==1 or ring==4)
166  if (p == CSCPart::ME11){
167  if (alct.getKeyWG() >= 10)
168  p = CSCPart::ME1B;
169  else
170  p = CSCPart::ME1A;
171  }
172 
173  const auto& mymap1 = getLUT()->get_gem_pad_to_csc_hs(theParity, p);
174  // GEM pad number is counting from 1
175  // keyStrip from mymap: for ME1b 0-127 and for ME1a 0-95
176  // keyStrip for CLCT: for ME1b 0-127 and for ME1a 128-223
177  keyStrip = mymap1[gem2.pad(2) - 1];
178  if (p == CSCPart::ME1A and keyStrip <= CSCConstants::MAX_HALF_STRIP_ME1B)
179  keyStrip += CSCConstants::MAX_HALF_STRIP_ME1B + 1;
180  keyWG = alct.getKeyWG();
181 
182  if ((not doesWiregroupCrossStrip(keyWG, keyStrip)) and p == CSCPart::ME1B and keyWG <= 15){
183  //try ME1A as strip and WG do not cross
184  p = CSCPart::ME1A;
185  const auto& mymap2 = getLUT()->get_gem_pad_to_csc_hs(theParity, p);
186  keyStrip = mymap2[gem2.pad(2) - 1] + CSCConstants::MAX_HALF_STRIP_ME1B + 1;
187  }
188 
189  pattern = promoteALCTGEMpattern_ ? 10 : 0;
190  quality = promoteALCTGEMquality_ ? 15 : 11;
191  bx = alct.getBX();
192  thisLCT.setALCT(getBXShiftedALCT(alct));
193  thisLCT.setGEM1(gem2.first());
194  thisLCT.setGEM2(gem2.second());
196  }
197  else if (clct.isValid() and gem2.isValid() and not alct.isValid()) {
198  auto p(getCSCPart(clct.getKeyStrip()));
199  const auto& mymap2 = getLUT()->get_gem_roll_to_csc_wg(theParity, p);
200  pattern = encodePattern(clct.getPattern());
201  quality = promoteCLCTGEMquality_ ? 15 : 11;
202  bx = gem2.bx(1) + CSCConstants::LCT_CENTRAL_BX;
203  keyStrip = clct.getKeyStrip();
204  // choose the corresponding wire-group in the middle of the partition
205  keyWG = mymap2[gem2.roll()];
206  bend = clct.getBend();
207  thisLCT.setCLCT(clct);
208  thisLCT.setGEM1(gem2.first());
209  thisLCT.setGEM2(gem2.second());
211  }
212 
213  valid = doesWiregroupCrossStrip(keyWG, keyStrip) ? 1 : 0;
214  if (valid == 0)
215  LogTrace("CSCGEMCMotherboard") << "Warning!!! wiregroup and strip pair are not crossing each other"
216  <<" detid "<<cscId_ <<" with wiregroup "<< keyWG << "keyStrip "<< keyStrip <<" \n";
217 
218  // fill the rest of the properties
219  thisLCT.setTrknmb(trknmb);
220  thisLCT.setValid(valid);
221  thisLCT.setQuality(quality);
222  thisLCT.setWireGroup(keyWG);
223  thisLCT.setStrip(keyStrip);
224  thisLCT.setPattern(pattern);
225  thisLCT.setBend(bend);
226  thisLCT.setBX(bx);
227  thisLCT.setMPCLink(0);
228  thisLCT.setBX0(0);
229  thisLCT.setSyncErr(0);
230  thisLCT.setCSCID(theTrigChamber);
231 
232  // future work: add a section that produces LCTs according
233  // to the new LCT dataformat (not yet defined)
234 
235  // return new LCT
236  return thisLCT;
237 }
238 
239 
241 {
242  // this only works for ME1A!
243  const auto& mymap = (getLUT()->get_csc_wg_to_gem_roll(theParity));
244  for (unsigned i=0; i<mymap.size(); i++) {
245  // overlap region are WGs 10-15
246  if ((i < 10) or (i > 15)) continue;
247  if ((mymap[i].first <= roll) and (roll <= mymap[i].second)) return true;
248  }
249  return false;
250 }
251 
252 bool CSCGEMMotherboard::isGEMDetId(unsigned int p) const
253 {
254  return (DetId(p).subdetId() == MuonSubdetId::GEM and
255  DetId(p).det() == DetId::Muon);
256 }
257 
259 {
260  return p.bx();
261 }
262 
264 {
265  return p.bx(1);
266 }
267 
269 {
270  return GEMDetId(p.first).roll();
271 }
272 
274 {
275  return p.second.roll();
276 }
277 
279 {
280  return (getLUT()->get_csc_wg_to_gem_roll(theParity))[alct.getKeyWG()].first;
281 }
282 
284 {
285  return p.pad();
286 }
287 
289 {
290  // average pad number for a GEMCoPad
291  return 0.5*(p.pad(1) + p.pad(2));
292 }
293 
294 float CSCGEMMotherboard::getPad(const CSCCLCTDigi& clct, enum CSCPart part) const
295 {
296  const auto& mymap = (getLUT()->get_csc_hs_to_gem_pad(theParity, part));
297  int keyStrip = clct.getKeyStrip();
298  //ME1A part, convert halfstrip from 128-223 to 0-95
299  if (part == CSCPart::ME1A and keyStrip > CSCConstants::MAX_HALF_STRIP_ME1B)
300  keyStrip = keyStrip - CSCConstants::MAX_HALF_STRIP_ME1B -1;
301  return 0.5*(mymap[keyStrip].first + mymap[keyStrip].second);
302 
303 }
304 
306 {
308  generator_->setGEMGeometry(gem_g);
309 }
310 
311 void CSCGEMMotherboard::printGEMTriggerPads(int bx_start, int bx_stop, enum CSCPart part)
312 {
313  LogTrace("CSCGEMMotherboard") << "------------------------------------------------------------------------" << std::endl;
314  LogTrace("CSCGEMMotherboard") << "* GEM trigger pads: " << std::endl;
315 
316  for (int bx = bx_start; bx <= bx_stop; bx++) {
317  const auto& in_pads = pads_[bx];
318  LogTrace("CSCGEMMotherboard") << "N(pads) BX " << bx << " : " << in_pads.size() << std::endl;
319 
320  for (const auto& pad : in_pads){
321  LogTrace("CSCGEMMotherboard") << "\tdetId " << GEMDetId(pad.first) << ", pad = " << pad.second;
322  const auto& roll_id(GEMDetId(pad.first));
323 
324  if (part==CSCPart::ME11 and isPadInOverlap(GEMDetId(roll_id).roll()))
325  LogTrace("CSCGEMMotherboard") << " (in overlap)" << std::endl;
326  else
327  LogTrace("CSCGEMMotherboard") << std::endl;
328  }
329  }
330 }
331 
332 
333 void CSCGEMMotherboard::printGEMTriggerCoPads(int bx_start, int bx_stop, enum CSCPart part)
334 {
335  LogTrace("CSCGEMMotherboard") << "------------------------------------------------------------------------" << std::endl;
336  LogTrace("CSCGEMMotherboard") << "* GEM trigger coincidence pads: " << std::endl;
337 
338  for (int bx = bx_start; bx <= bx_stop; bx++) {
339  const auto& in_pads = coPads_[bx];
340  LogTrace("CSCGEMMotherboard") << "N(copads) BX " << bx << " : " << in_pads.size() << std::endl;
341 
342  for (const auto& pad : in_pads){
343  LogTrace("CSCGEMMotherboard") << "\tdetId " << GEMDetId(pad.first) << ", pad = " << pad.second;
344  const auto& roll_id(GEMDetId(pad.first));
345 
346  if (part==CSCPart::ME11 and isPadInOverlap(GEMDetId(roll_id).roll())) LogTrace("CSCGEMMotherboard") << " (in overlap)" << std::endl;
347  else LogTrace("CSCGEMMotherboard") << std::endl;
348  }
349  }
350 }
351 
352 
354  const CSCCLCTDigi& cLCT, int gemlayers) const
355 {
356  // Either ALCT or CLCT is invalid
357  if (!(aLCT.isValid()) || !(cLCT.isValid())) {
358 
359  // No CLCT
360  if (aLCT.isValid() && !(cLCT.isValid()))
361  return LCT_Quality::NO_CLCT;
362 
363  // No ALCT
364  else if (!(aLCT.isValid()) && cLCT.isValid())
365  return LCT_Quality::NO_ALCT;
366 
367  // No ALCT and no CLCT
368  else
369  return LCT_Quality::INVALID;
370  }
371  // Both ALCT and CLCT are valid
372  else {
373  const int pattern(cLCT.getPattern());
374 
375  // Layer-trigger in CLCT
376  if (pattern == 1)
377  return LCT_Quality::CLCT_LAYER_TRIGGER;
378 
379  // Multi-layer pattern in CLCT
380  else {
381  // ALCT quality is the number of layers hit minus 3.
382  bool a4 = false;
383 
384  // Case of ME11 with GEMs: require 4 layers for ALCT
385  if (theStation==1) a4 = aLCT.getQuality() >= 1;
386 
387  // Case of ME21 with GEMs: require 4 layers for ALCT+GEM
388  if (theStation==2) a4 = aLCT.getQuality() + gemlayers >=1;
389 
390  // CLCT quality is the number of layers hit.
391  const bool c4((cLCT.getQuality() >= 4) or (cLCT.getQuality() >= 3 and gemlayers>=1));
392 
393  // quality = 4; "reserved for low-quality muons in future"
394 
395  // marginal anode and cathode
396  if (!a4 && !c4)
397  return LCT_Quality::MARGINAL_ANODE_CATHODE;
398 
399  // HQ anode, but marginal cathode
400  else if ( a4 && !c4)
401  return LCT_Quality::HQ_ANODE_MARGINAL_CATHODE;
402 
403  // HQ cathode, but marginal anode
404  else if (!a4 && c4)
405  return LCT_Quality::HQ_CATHODE_MARGINAL_ANODE;
406 
407  // HQ muon, but accelerator ALCT
408  else if ( a4 && c4) {
409 
410  if (aLCT.getAccelerator())
411  return LCT_Quality::HQ_ACCEL_ALCT;
412 
413  else {
414  // quality = 9; "reserved for HQ muons with future patterns
415  // quality = 10; "reserved for HQ muons with future patterns
416 
417  // High quality muons are determined by their CLCT pattern
418  if (pattern == 2 || pattern == 3)
419  return LCT_Quality::HQ_PATTERN_2_3;
420 
421  else if (pattern == 4 || pattern == 5)
422  return LCT_Quality::HQ_PATTERN_4_5;
423 
424  else if (pattern == 6 || pattern == 7)
425  return LCT_Quality::HQ_PATTERN_6_7;
426 
427  else if (pattern == 8 || pattern == 9)
428  return LCT_Quality::HQ_PATTERN_8_9;
429 
430  else if (pattern == 10)
431  return LCT_Quality::HQ_PATTERN_10;
432 
433  else {
434  if (infoV >= 0) edm::LogWarning("L1CSCTPEmulatorWrongValues")
435  << "+++ findQuality: Unexpected CLCT pattern id = "
436  << pattern << "+++\n";
437  return LCT_Quality::INVALID;
438  }
439  }
440  }
441  }
442  }
443  return LCT_Quality::INVALID;
444 }
445 
446 
447 template <> const matchesBX<GEMPadDigi>&
448 CSCGEMMotherboard::getPads<GEMPadDigi>() const
449 {
450  return pads_;
451 }
452 
453 template <> const matchesBX<GEMCoPadDigi>&
454 CSCGEMMotherboard::getPads<GEMCoPadDigi>() const
455 {
456  return coPads_;
457 }
458 
459 template <>
460 int CSCGEMMotherboard::getMaxDeltaBX<GEMPadDigi>() const
461 {
462  return maxDeltaBXPad_;
463 }
464 
465 template <>
466 int CSCGEMMotherboard::getMaxDeltaBX<GEMCoPadDigi>() const
467 {
468  return maxDeltaBXCoPad_;
469 }
470 
471 template <>
472 int CSCGEMMotherboard::getLctTrigEnable<CSCALCTDigi>() const
473 {
474  return alct_trig_enable;
475 }
476 
477 template <>
478 int CSCGEMMotherboard::getLctTrigEnable<CSCCLCTDigi>() const
479 {
480  return clct_trig_enable;
481 }
int getQuality() const
return quality of a pattern (number of layers hit!)
Definition: CSCCLCTDigi.h:41
bool isValid() const
Definition: GEMPadDigi.cc:48
void retrieveGEMPads(const GEMPadDigiCollection *pads, unsigned id)
T getParameter(std::string const &) const
match< GEMCoPadDigi > GEMCoPadDigiId
void setALCT(const CSCALCTDigi &alct)
void setGEM2(const GEMPadDigi &gem)
static constexpr int GEM
Definition: MuonSubdetId.h:15
unsigned int clct_trig_enable
void setWireGroup(unsigned int wiregroup)
set wiregroup number
void setBend(unsigned int b)
set bend
std::unique_ptr< CSCUpgradeMotherboardLUTGenerator > generator_
CSCALCTDigi getBXShiftedALCT(const CSCALCTDigi &) const
bool isValid() const
check ALCT validity (1 - valid ALCT)
Definition: CSCALCTDigi.h:32
GEMCoPadDigiIdsBX coPads_
void setBX0(unsigned int b)
set bx0
int roll() const
Definition: GEMDetId.h:80
constexpr uint32_t rawId() const
get the raw id
Definition: DetId.h:50
std::vector< int > get_gem_roll_to_csc_wg(Parity par, int layer=1) const
void setQuality(unsigned int q)
set quality code
int getBX(const GEMPadDigi &p) const
static constexpr TimeType INVALID
Definition: Time.h:33
int pad(int l) const
Definition: GEMCoPadDigi.cc:38
virtual bool doesWiregroupCrossStrip(int key_wg, int key_strip) const
CSCDetId cscId_
Definition: CSCBaseboard.h:46
Definition: AMC13Event.h:6
std::vector< GEMCoPadDigi > gemCoPadV
int getBend() const
return bend
Definition: CSCCLCTDigi.h:59
void setMPCLink(const uint16_t &link)
Set mpc link number after MPC sorting.
U second(std::pair< T, U > const &p)
bool isValid() const
Definition: GEMCoPadDigi.cc:32
const unsigned theTrigChamber
Definition: CSCBaseboard.h:37
match< GEMPadDigi > GEMPadDigiId
void setPattern(unsigned int p)
set pattern
void setValid(unsigned int v)
set valid
std::unique_ptr< GEMCoPadProcessor > coPadProcessor
virtual void run(const CSCWireDigiCollection *wiredc, const CSCComparatorDigiCollection *compdc, const GEMPadDigiCollection *gemPads)=0
void setSyncErr(unsigned int s)
set syncErr
int bx(int l) const
Definition: GEMCoPadDigi.cc:46
void setStrip(unsigned int s)
set strip
unsigned int findQualityGEM(const CSCALCTDigi &, const CSCCLCTDigi &, int gemlayer) const
virtual std::vector< std::pair< int, int > > get_csc_hs_to_gem_pad(Parity par, enum CSCPart) const =0
The Signals That Services Can Subscribe To This is based on ActivityRegistry and is current per Services can connect to the signals distributed by the ActivityRegistry in order to monitor the activity of the application Each possible callback has some defined which we here list in angle e< void, edm::EventID const &, edm::Timestamp const & > We also list in braces which AR_WATCH_USING_METHOD_ is used for those or
Definition: Activities.doc:12
int pad() const
Definition: GEMPadDigi.h:27
void printGEMTriggerCoPads(int bx_start, int bx_stop, enum CSCPart)
unsigned int encodePattern(const int clctPattern) const
GEMPadDigi first() const
Definition: GEMCoPadDigi.h:30
bool isValid() const
check CLCT validity (1 - valid CLCT)
Definition: CSCCLCTDigi.h:35
int getRoll(const GEMPadDigiId &p) const
void setCSCID(unsigned int c)
set cscID
unsigned theChamber
Definition: CSCBaseboard.h:40
bool isGEMDetId(unsigned int) const
int roll() const
Definition: GEMCoPadDigi.h:26
#define LogTrace(id)
const GEMSuperChamber * superChamber(GEMDetId id) const
Definition: GEMGeometry.cc:91
int getBX() const
return BX - five low bits of BXN counter tagged by the ALCT
Definition: CSCALCTDigi.h:65
bool isPadInOverlap(int roll) const
float getPad(const GEMPadDigi &) const
virtual std::vector< int > get_gem_pad_to_csc_hs(Parity par, enum CSCPart) const =0
CSCCorrelatedLCTDigi constructLCTsGEM(const CSCALCTDigi &alct, const GEMCoPadDigi &gem, int i) const
Definition: DetId.h:18
edm::ParameterSet tmbParams_
Definition: CSCBaseboard.h:61
int getQuality() const
return quality of a pattern
Definition: CSCALCTDigi.h:38
int getAccelerator() const
Definition: CSCALCTDigi.h:45
unsigned theRegion
Definition: CSCBaseboard.h:38
void setBX(unsigned int b)
set bx
int bx() const
Definition: GEMPadDigi.h:28
int getPattern() const
return pattern
Definition: CSCCLCTDigi.h:47
part
Definition: HCALResponse.h:20
MuonDigiCollection< GEMDetId, GEMPadDigi > GEMPadDigiCollection
const unsigned theStation
Definition: CSCBaseboard.h:34
GEMPadDigi second() const
Definition: GEMCoPadDigi.h:31
unsigned int alct_trig_enable
virtual const CSCGEMMotherboardLUT * getLUT() const =0
GEMPadDigiIdsBX pads_
~CSCGEMMotherboard() override
int getKeyStrip() const
Definition: CSCCLCTDigi.h:94
const GEMGeometry * gem_g
void setTrknmb(const uint16_t number)
Set track number (1,2) after sorting LCTs.
void setCLCT(const CSCCLCTDigi &clct)
int getKeyWG() const
return key wire group
Definition: CSCALCTDigi.h:59
void setGEM1(const GEMPadDigi &gem)
void printGEMTriggerPads(int bx_start, int bx_stop, enum CSCPart)
std::vector< std::pair< int, int > > get_csc_wg_to_gem_roll(Parity par, int layer=1) const
enum CSCPart getCSCPart(int keystrip) const