All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Modules Pages
ExceptionSvc.cpp
Go to the documentation of this file.
1 // ============================================================================
2 // Include files
3 // ============================================================================
4 // STD & STL
5 // ============================================================================
6 #include <cassert>
7 #include <algorithm>
8 // ============================================================================
9 // GaudiKernel
10 // ============================================================================
12 // ============================================================================
13 //Local
14 // ============================================================================
15 #include "ExceptionSvc.h"
16 // ============================================================================
17 
18 #include <boost/regex.hpp>
19 
20 using namespace std;
21 
22 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
23 
25 
26 inline void toupper(std::string &s)
27 {
28  std::transform(s.begin(), s.end(), s.begin(),
29  (int(*)(int)) toupper);
30 }
31 
32 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
33 
37  if ( status.isFailure() ) { return status ; }
38 
39  string key = m_mode_exc_s.value();
40 
41  auto loc = key.find(" ");
42  std::string mode = key.substr(0,loc);
43 
44  toupper(mode);
45 
46  if (mode == "NONE") { m_mode_exc = NONE;
47  } else if (mode == "ALL") { m_mode_exc = ALL;
48  } else {
49  error() << "Unknown mode for Exception handling: \"" << mode
50  << "\". Default must be one of \"ALL\" or \"NONE\"" << endmsg;
52  return StatusCode::FAILURE;
53  }
54 
55  if (loc == string::npos) {
56  key.clear();
57  } else {
58  key = key.substr(loc+1);
59  }
60 
61  std::string VAL, TAG;
62 
63  static const boost::regex exp{"[[:space:]]*([^[:space:]]+)[[:space:]]*=[[:space:]]*([^[:space:]]+)"};
64  static const auto tok_end = boost::sregex_iterator();
65  for (auto tok_iter = boost::sregex_iterator(begin(key), end(key), exp);
66  tok_iter != tok_end; ++tok_iter)
67  {
68  TAG = (*tok_iter)[1];
69  VAL = (*tok_iter)[2];
70  toupper(VAL);
71 
72  if (VAL == "SUCCESS") { m_retCodesExc[TAG] = SUCCESS;
73  } else if ( VAL == "FAILURE" ) { m_retCodesExc[TAG] = FAILURE;
74  } else if ( VAL == "REVOVERABLE" ) { m_retCodesExc[TAG] = RECOVERABLE;
75  } else if ( VAL == "RETHROW" ) { m_retCodesExc[TAG] = RETHROW;
76  } else if ( VAL == "DEFAULT" ) { m_retCodesExc[TAG] = DEFAULT;
77  } else {
78  error() << "In JobOpts: unknown return code \"" << VAL
79  << "\" for Algorithm " << TAG << std::endl
80  << " Must be one of: DEFAULT, SUCCESS, FAILURE, RECOVERABLE, RETHROW"
81  << endmsg;
83  return StatusCode::FAILURE;
84  }
85 
86  if ( msgLevel( MSG::DEBUG ) )
87  debug() << "Will catch exceptions thrown by: " << TAG
88  << " -> action: " << VAL << endmsg;
89 
90  }
91 
92  // now process errors
93  key = m_mode_err_s.value();
94 
95  loc = key.find(" ");
96  mode = key.substr(0,loc);
97 
98  toupper(mode);
99 
100  if (mode == "NONE") { m_mode_err = NONE;
101  } else if (mode == "ALL") { m_mode_err = ALL;
102  } else {
103  error() << "Unknown mode for Error handling: \"" << mode
104  << "\". Default must be one of \"ALL\" or \"NONE\"" << endmsg;
106  return StatusCode::FAILURE;
107  }
108 
109  if (loc == string::npos) {
110  key.clear();
111  } else {
112  key = key.substr(loc+1);
113  }
114 
115  for (auto tok_iter = boost::sregex_iterator(begin(key), end(key), exp);
116  tok_iter != tok_end; ++tok_iter)
117  {
118  TAG = (*tok_iter)[1];
119  VAL = (*tok_iter)[2];
120  toupper(VAL);
121 
122  if (VAL == "SUCCESS") { m_retCodesErr[TAG] = SUCCESS;
123  } else if ( VAL == "FAILURE" ) { m_retCodesErr[TAG] = FAILURE;
124  } else if ( VAL == "RECOVERABLE" ) { m_retCodesErr[TAG] = RECOVERABLE;
125  } else {
126  error() << "In JobOpts: unknown return code \"" << VAL
127  << "\" for Algorithm " << TAG << std::endl
128  << " Must be one of: SUCCESS, FAILURE, RECOVERABLE"
129  << endmsg;
131  return StatusCode::FAILURE;
132  }
133 
134  if ( msgLevel( MSG::DEBUG ) )
135  debug() << "Will process Errors returned by: " << TAG
136  << " -> action: " << VAL << endmsg;
137  }
138  return status;
139 }
140 
141 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
142 
144 ( const INamedInterface& alg ,
145  const StatusCode& st ) const
146 {
147  if ( msgLevel( MSG::DEBUG ) )
148  debug() << "Handling Error from " << alg.name() << endmsg;
149 
150  // is this Alg special?
151  auto i = m_retCodesErr.find(alg.name());
152  if ( i != m_retCodesErr.end()) {
153  switch ( i->second ) {
154  case SUCCESS: return StatusCode::SUCCESS;
155  case FAILURE: return StatusCode::FAILURE;
156  case RECOVERABLE: return StatusCode::RECOVERABLE;
157  // should never get here
158  case RETHROW: break;
159  case DEFAULT: break;
160  }
161 
162  } else {
163 
164  if (m_mode_err == ALL) return StatusCode::FAILURE; // turn it into FAILURE
165  assert (m_mode_err == NONE );
166  // don't touch the return code
167  return st;
168  }
169  return StatusCode::FAILURE;
170 }
171 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
172 
174 ( const INamedInterface& alg ) const
175 {
176 
177  // is this Alg special?
178  auto i = m_retCodesExc.find(alg.name());
179  if ( i != m_retCodesExc.end()) {
180 
181  switch ( i->second ) {
182  case DEFAULT: return StatusCode::FAILURE; // there is no default
183  case SUCCESS: return StatusCode::SUCCESS;
184  case FAILURE: return StatusCode::FAILURE;
185  case RECOVERABLE: return StatusCode::RECOVERABLE;
186  case RETHROW: throw;
187  }
188  }
189 
190  if (m_mode_exc == ALL) { throw; }
191  assert (m_mode_exc == NONE);
192  return StatusCode::FAILURE;
193 }
194 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
195 
197 ( const INamedInterface& alg ) const
198 {
199  if ( msgLevel( MSG::DEBUG ) )
200  debug() << "Handling unknown exception for " << alg.name() << endmsg;
201  return process(alg);
202 }
203 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
204 
206 ( const INamedInterface& alg ,
207  const std::exception & exc ) const
208 {
209  if ( msgLevel( MSG::DEBUG ) )
210  debug() << "Handling std:except: \"" << exc.what() << "\" for "
211  << alg.name() << endmsg;
212  return process(alg) ;
213 }
214 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
215 
217 ( const INamedInterface& alg ,
218  const GaudiException & exc ) const
219 {
220  if ( msgLevel( MSG::DEBUG ) )
221  debug() << "Handling GaudiException: \"" << exc << "\" for "
222  << alg.name() << endmsg;
223  return process(alg);
224 }
225 
226 // ============================================================================
227 // The END
228 // ============================================================================
StatusCode initialize() override
Definition: Service.cpp:64
int ALL
message levels --------------------------------------------------------—
Definition: Constants.py:11
Define general base for Gaudi exception.
T exp(T...args)
T endl(T...args)
STL namespace.
T end(T...args)
bool isFailure() const
Test for a status code of FAILURE.
Definition: StatusCode.h:84
#define DECLARE_COMPONENT(type)
Definition: PluginService.h:36
STL class.
T toupper(T...args)
T what(T...args)
This class is used for returning status codes from appropriate routines.
Definition: StatusCode.h:26
Simple implementation of IExceptionSvc abstract interface.
Definition: ExceptionSvc.h:19
StatusCode initialize() override
initialize the service
T clear(T...args)
STL class.
StatusCode handle(const INamedInterface &o, const GaudiException &e) const override
Handle caught GaudiExceptions.
IInterface compliant class extending IInterface with the name() method.
T find(T...args)
T begin(T...args)
StatusCode handleErr(const INamedInterface &o, const StatusCode &s) const override
Handle errors.
string s
Definition: gaudirun.py:245
T substr(T...args)
T transform(T...args)
virtual StatusCode process(const INamedInterface &o) const
MsgStream & endmsg(MsgStream &s)
MsgStream Modifier: endmsg. Calls the output method of the MsgStream.
Definition: MsgStream.h:244
virtual const std::string & name() const =0
Retrieve the name of the instance.