CMS 3D CMS Logo

 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Pages
TriggerSelector.cc
Go to the documentation of this file.
1 #include "TriggerSelector.h"
2 
6 
7 #include <iostream>
8 #include <boost/regex.hpp>
9 #include <algorithm>
10 #include <cassert>
11 
12 namespace dqmservices
13 {
14 
15  //compatibility constructor
16 
18  (
19  Strings const& pathspecs,
20  Strings const& names
21  ):
22  useOld_(true)
23  {
24  acceptAll_=false;
25  eventSelector_.reset( new edm::EventSelector(pathspecs,names));
26  }
27 
29  (
31  Strings const& triggernames,
32  bool old_
33  ):
34  useOld_(old_)
35  {
36  acceptAll_=false;
37  if (old_) {
38  //old mode forced
39  acceptAll_=false;
40  eventSelector_.reset( new edm::EventSelector(config, triggernames));
41  return;
42  }
43  if (!config.empty()) {
44  //let's see if non empty TriggerSelector is present
45  try {
46  std::string myPath = trim(config.getParameter<std::string>("TriggerSelector"));
47  if (!myPath.empty()) {
48  init(myPath, triggernames);
49  return;
50  }
51  }
52  catch(...) {}
53 
54  //now try with the SelectEvents
55  try {
56  Strings paths;
57  paths = config.getParameter<Strings>("SelectEvents");
58  if (!paths.empty()) {
59  useOld_=true;
60  eventSelector_.reset( new edm::EventSelector(config, triggernames));
61  return;
62  }
63  }
64  catch(...) {}
65  }
66  //if selection parameters aren't present, don't do selection
67  //log
68  acceptAll_=true;
69  }
70 
72  (
73  std::string const & expression,
74  Strings const& triggernames
75  ):
76  useOld_(false)
77  {
78  init (trim(expression),triggernames);
79  }
80 
81  void
83  (
84  std::string const& expression,
85  Strings const& triggernames
86  )
87  {
88  //debug_ = true;
89  if (expression.empty())
90  {
91  acceptAll_ = true;
92  return;
93  }
94  if (expression.size()==1 && expression.at(0)=='*') acceptAll_=true;
95  else acceptAll_=false;
96 
97  //replace all possible alternate operators (.AND. and .OR.)
98  {
99  using namespace boost;
101  temp = regex_replace( expression , regex(".AND."), "&&");
102  expression_ = regex_replace( temp, regex(".and."), "&&");
103  temp = regex_replace( expression_, regex(".OR."), "||");
104  expression_ = regex_replace( temp, regex(".or."), "||");
105  }
106 
107  //build decision tree
108  masterElement_.reset( new TreeElement(expression_,triggernames));
109  }
110 
111  /*
112  Obsolete
113  */
114  std::vector<std::string>
116  {
118  }
119 
121  {
122  if (useOld_) {
123  return eventSelector_->acceptEvent(tr);
124  }
125 
126  if (acceptAll_) return true;
127 
128  return masterElement_->returnStatus(tr);
129  }
130 
131  bool
133  (
134  unsigned char const* array_of_trigger_results,
135  int number_of_trigger_paths
136  ) const
137  {
138  if (useOld_)
139  return eventSelector_->acceptEvent(array_of_trigger_results,number_of_trigger_paths);
140 
141  if (acceptAll_) return true;
142 
143  // Form HLTGlobalStatus object to represent the array_of_trigger_results
144  edm::HLTGlobalStatus tr(number_of_trigger_paths);
145  int byteIndex = 0;
146  int subIndex = 0;
147  for (int pathIndex = 0; pathIndex < number_of_trigger_paths; ++pathIndex)
148  {
149  int state = array_of_trigger_results[byteIndex] >> (subIndex * 2);
150  state &= 0x3;
151  edm::HLTPathStatus pathStatus(static_cast<edm::hlt::HLTState>(state));
152  tr[pathIndex] = pathStatus;
153  ++subIndex;
154  if (subIndex == 4)
155  { ++byteIndex;
156  subIndex = 0;
157  }
158  }
159  // Now make the decision, based on the HLTGlobalStatus tr,
160  // which we have created from the supplied array of results
161  masterElement_->returnStatus(tr);
162  return masterElement_->returnStatus(tr);
163  }
164 
165 
167  (
168  std::string const& inputString,
169  Strings const& tr,
170  TreeElement* parentElement
171  ) :
172  op_(NonInit),
173  trigBit_(-1)
174  {
175  std::string str_ = trim(inputString);
176  children_.clear();
177  parent_ = parentElement;
178 
179  size_t offset_=0;
180  bool occurrences_=false;
181 
182  if (str_.empty())
184  << "Syntax Error (empty element)" << std::endl;
185 
186  static const size_t bopsSize_ = 2;
187  static const std::string binaryOperators_[bopsSize_] = {"||","&&"};
188 
189  for (size_t opr=0;opr<bopsSize_;opr++) {
190  bool exitloop_=false;
191  while(!exitloop_) {
192  size_t t_end_;
193 
194  std::string tmpStr = str_.substr(offset_);
195  t_end_ = tmpStr.find(binaryOperators_[opr]);
196  if (debug_) std::cout << "offset: " << offset_ << " length: " << t_end_ <<" string: " << tmpStr << std::endl;
197 
198  if (t_end_ == std::string::npos) {
199  //right side element
200  if (occurrences_) children_.push_back(new TreeElement(tmpStr,tr,this));
201  break;
202  }
203  t_end_ += offset_;
204  if (t_end_==0 || t_end_+2>=str_.size())
205  throw edm::Exception(edm::errors::Configuration) << "Syntax Error (operator is not unary)\n";
206  else {
207  //count bracket in preceeding part
208  size_t brackets_=0;
209  for (size_t k=offset_;k<t_end_;k++) {
210  if (str_.at(k)=='(')
211  {
212  brackets_++;
213  }
214  else if (str_.at(k)==')')
215  {
216  if (brackets_ == 0)
217  {
219  << "Syntax Error (brackets)\n";
220  }
221  else
222  {
223  brackets_--;
224  }
225  }
226  }
227  if (brackets_==0) {
228  std::string next = str_.substr(offset_,t_end_-offset_);
229  children_.push_back(new TreeElement(next,tr,this));
230  occurrences_=true;
231  offset_ = t_end_+2;
232  }
233  else {
234  //operator is inside brackets, find another
235  int bracketcnt_ = 0;
236  for (size_t k=offset_;true;k++) {
237  if (k>=str_.size()) {
238  if (bracketcnt_!=0)
240  << "Syntax Error (brackets)\n";
241  exitloop_=true;
242  if (occurrences_) {
243  children_.push_back(new TreeElement(str_.substr(offset_),tr,this));
244  }
245  break;
246  }
247  //look for another operator
248  if (k>=t_end_+2 && bracketcnt_==0) {
249  std::string temp = str_.substr(k);
250  size_t pos = temp.find(binaryOperators_[opr]);
251  if (pos == std::string::npos) {
252  exitloop_=true;
253  if (occurrences_) {
254  children_.push_back(new TreeElement(str_.substr(offset_),tr,this));
255  }
256  break;
257  }
258  else {
259  int brcount_ = 0;
260  for (size_t s=0;s<pos;s++) {
261  //counting check of brackets from last position to operator
262  if (temp.at(pos)=='(')
263  {
264  brcount_++;
265  }
266  else if (temp.at(pos)==')')
267  {
268  if (brcount_ == 0)
269  {
271  << "Syntax error (brackets)\n";
272  }
273  else
274  {
275  brcount_--;
276  }
277  }
278  }
279  if (brcount_!=0)
281  << "Syntax error (brackets)\n";
282 
283  children_.push_back(new TreeElement(str_.substr(offset_,pos+k),tr,this));
284  offset_=k+pos+2;
285  occurrences_=true;
286  if (offset_>=str_.size())
288  << "Syntax Error (operator is not unary)\n";
289  break;
290  }
291 
292  }
293 
294 
295  if (str_.at(k)=='(') bracketcnt_++;
296  if (str_.at(k)==')') bracketcnt_--;
297 
298  }
299  }
300  }
301 
302  }
303  if (occurrences_) {
304  if (opr==0) op_=OR;
305  else op_=AND;
306  return;
307  }
308  }
309 
310  if (str_.empty()) {
311  op_=AND;
312  if (debug_) std::cout << "warning: empty element (will return true)"<< std::endl;
313  return;
314  }
315 
316  if (str_.at(0)=='!') {
317  op_=NOT;
318  std::string next = str_.substr(1);
319  children_.push_back(new TreeElement(next,tr,this));
320  return;
321  }
322  size_t beginBlock_ =str_.find('(');
323  size_t endBlock_ =str_.rfind(')');
324  bool found_lbracket = (beginBlock_ != std::string::npos);
325  bool found_rbracket = (endBlock_ != std::string::npos);
326 
327  if (found_lbracket != found_rbracket) {
328  throw edm::Exception(edm::errors::Configuration) << "Syntax Error (brackets)\n";
329  }
330  else if (found_lbracket && found_rbracket)
331  {
332  if (beginBlock_>=endBlock_) {
333  throw edm::Exception(edm::errors::Configuration) << "Syntax Error (brackets)\n";
334  }
335  if (beginBlock_!=0 || endBlock_!=str_.size()-1)
336  throw edm::Exception(edm::errors::Configuration) << "Syntax Error (invalid character)\n";
337 
338  std::string next = str_.substr(beginBlock_+1,endBlock_-beginBlock_-1);
339 
340  children_.push_back(new TreeElement(next,tr,this));
341  op_=BR; //a bracket
342  return;
343  }
344  else if (!found_lbracket && !found_rbracket) //assume single trigger or wildcard (parsing)
345  {
346  bool ignore_if_missing = true;
347  size_t chr_pos = str_.find("@");
348  if (chr_pos!= std::string::npos) {
349  ignore_if_missing=false;
350  str_=str_.substr(0,chr_pos);
351  }
352 
353  std::vector<Strings::const_iterator> matches = edm::regexMatch(tr,str_);
354  if (matches.empty()) {
355  if (!ignore_if_missing)// && !edm::is_glob(str_))
356  throw edm::Exception(edm::errors::Configuration) << "Trigger name (or match) not present" << std::endl;
357  else {
358  if (debug_)
359  std::cout << "TriggerSelector: Couldn't match any triggers from: "<< str_<< std::endl
360  << " Node will not be added "<< std::endl;
361  op_=OR;
362  return;
363  }
364  }
365  if (matches.size()==1) {
366  //Single Trigger match
367  trigBit_ = distance(tr.begin(),matches[0]);
368  if (debug_) std::cout << "added trigger path: " << trigBit_ << std::endl;
369  return;
370  }
371  if (matches.size()>1) {
372  op_=OR;
373  for (size_t l=0;l<matches.size();l++)
374  children_.push_back(new TreeElement(*(matches[l]),tr,this));
375  }
376  }
377  }
378 
380  {
381  if (!input.empty())
382  {
383  std::string::size_type pos = input.find_first_not_of(" ");
384  if (pos != std::string::npos)
385  input.erase(0,pos);
386 
387  pos = input.find_last_not_of(" ");
388  if (pos != std::string::npos)
389  input.erase(pos+1);
390  }
391  return input;
392  }
393 
395  {
397  if (!input.empty()) {
398  for (size_t pos=0;pos<input.size();pos++) {
399  char ch = input.at(pos);
400  if (ch=='&') output.append("&amp;");
401  else output.append(1,ch);
402  }
403  }
404  return output;
405  }
406 
407 
409  (
410  edm::HLTGlobalStatus const& trStatus
411  ) const
412  {
413 
414  if (children_.empty()) {
415 
416  if (op_==OR || op_==NOT) return false;
417  if (op_==AND || op_==BR) return true;
418 
419  if (trigBit_<0 || (unsigned int)trigBit_>=trStatus.size())
421  << "Internal Error: array out of bounds " << std::endl;
422 
423  if ((trStatus[trigBit_]).state() == edm::hlt::Pass) return true;
424  //else if ((trStatus[trigBit]).state() == edm::hlt::Fail) return false;
425 
426  return false;
427  }
428  if (op_==NOT) { //NEGATION
429  return !children_[0]->returnStatus(trStatus);
430  }
431  if (op_==BR) { //BRACKET
432  return children_[0]->returnStatus(trStatus);
433  }
434  if (op_==AND) { //AND
435  bool status = true;
436  for (size_t i=0;i<children_.size();i++) status = status && children_[i]->returnStatus(trStatus);
437  return status;
438  }
439  else if (op_==OR) { //OR
440  bool status = false;
441  for (size_t i=0;i<children_.size();i++) status = status || children_[i]->returnStatus(trStatus);
442  return status;
443  }
444  throw edm::Exception(edm::errors::Configuration) << "Internal error: reached end of returnStatus(...) op:state= " << op_ << std::endl;
445  return false;
446  }
447 
448 
450  {
451  for (std::vector<TreeElement*>::iterator it=children_.begin();it!=children_.end();it++)
452  delete *it;
453  children_.clear();
454  }
455 
456 }
T getParameter(std::string const &) const
bool empty() const
Definition: ParameterSet.h:217
int i
Definition: DBlmapReader.cc:9
static const HistoName names[]
int init
Definition: HydjetWrapper.h:62
static std::string trim(std::string input)
boost::shared_ptr< TreeElement > masterElement_
uint16_t size_type
static std::string const input
Definition: EdmProvDump.cc:43
static std::string makeXMLString(std::string const &input)
accept
Definition: HLTenums.h:19
unsigned int size() const
Get number of paths stored.
static std::vector< std::string > getEventSelectionVString(edm::ParameterSet const &pset)
TriggerSelector(Strings const &pathspecs, Strings const &names)
std::vector< std::vector< std::string >::const_iterator > regexMatch(std::vector< std::string > const &strings, boost::regex const &regexp)
Definition: RegexMatch.cc:30
boost::shared_ptr< edm::EventSelector > eventSelector_
void init(std::string const &path, Strings const &triggernames)
bool AND(const TrackBaseRef &track, const RecoTauQualityCuts::TrackQCutFuncCollection &cuts)
static std::vector< std::string > getEventSelectionVString(edm::ParameterSet const &pset)
bool acceptEvent(edm::TriggerResults const &) const
tuple cout
Definition: gather_cfg.py:121
tuple status
Definition: ntuplemaker.py:245
std::vector< TreeElement * > children_
TreeElement(std::string const &inputString, Strings const &tr, TreeElement *parentElement=NULL)
std::vector< std::string > Strings
bool returnStatus(edm::HLTGlobalStatus const &trStatus) const