CMS 3D CMS Logo

 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Pages
List of all members | Classes | Public Member Functions | Static Public Member Functions | Private Member Functions | Private Attributes
ExternalLHEProducer Class Reference

#include <Example/ExternalLHEProducer/src/ExternalLHEProducer.cc>

Inheritance diagram for ExternalLHEProducer:
edm::EDProducer edm::ProducerBase edm::ProductRegistryHelper

Classes

class  FileCloseSentry
 

Public Member Functions

 ExternalLHEProducer (const edm::ParameterSet &iConfig)
 
 ~ExternalLHEProducer ()
 
- Public Member Functions inherited from edm::EDProducer
 EDProducer ()
 
virtual ~EDProducer ()
 
- Public Member Functions inherited from edm::ProducerBase
 ProducerBase ()
 
void registerProducts (ProducerBase *, ProductRegistry *, ModuleDescription const &)
 
boost::function< void(const
BranchDescription &)> 
registrationCallback () const
 used by the fwk to register list of products More...
 
virtual ~ProducerBase ()
 

Static Public Member Functions

static void fillDescriptions (edm::ConfigurationDescriptions &descriptions)
 
- Static Public Member Functions inherited from edm::EDProducer
static const std::string & baseType ()
 
static void fillDescriptions (ConfigurationDescriptions &descriptions)
 
static void prevalidate (ConfigurationDescriptions &descriptions)
 

Private Member Functions

virtual void beginJob ()
 
virtual void beginLuminosityBlock (edm::LuminosityBlock &, edm::EventSetup const &)
 
virtual void beginRun (edm::Run &run, edm::EventSetup const &es)
 
int closeDescriptors (int preserve)
 
virtual void endLuminosityBlock (edm::LuminosityBlock &, edm::EventSetup const &)
 
virtual void endRun (edm::Run &, edm::EventSetup const &)
 
void executeScript ()
 
virtual void nextEvent ()
 
virtual void produce (edm::Event &, const edm::EventSetup &)
 
std::auto_ptr< std::string > readOutput ()
 

Private Attributes

std::vector< std::string > args_
 
uint32_t nEvents_
 
uint32_t npars_
 
std::string outputContents_
 
std::string outputFile_
 
boost::shared_ptr< lhef::LHEEventpartonLevel
 
std::auto_ptr< lhef::LHEReaderreader_
 
boost::shared_ptr
< lhef::LHERunInfo
runInfo
 
boost::shared_ptr
< lhef::LHERunInfo
runInfoLast
 
boost::ptr_deque
< LHERunInfoProduct
runInfoProducts
 
std::string scriptName_
 
bool wasMerged
 

Additional Inherited Members

- Public Types inherited from edm::EDProducer
typedef EDProducer ModuleType
 
typedef WorkerT< EDProducerWorkerType
 
- Public Types inherited from edm::ProducerBase
typedef
ProductRegistryHelper::TypeLabelList 
TypeLabelList
 
- Protected Member Functions inherited from edm::EDProducer
CurrentProcessingContext const * currentContext () const
 
- Protected Member Functions inherited from edm::ProducerBase
template<class TProducer , class TMethod >
void callWhenNewProductsRegistered (TProducer *iProd, TMethod iMethod)
 

Detailed Description

Description: [one line class summary]

Implementation: [Notes on implementation]

Definition at line 65 of file ExternalLHEProducer.cc.

Constructor & Destructor Documentation

ExternalLHEProducer::ExternalLHEProducer ( const edm::ParameterSet iConfig)
explicit

Definition at line 128 of file ExternalLHEProducer.cc.

References args_, and npars_.

128  :
129  scriptName_((iConfig.getParameter<edm::FileInPath>("scriptName")).fullPath().c_str()),
130  outputFile_(iConfig.getParameter<std::string>("outputFile")),
131  args_(iConfig.getParameter<std::vector<std::string> >("args")),
132  npars_(iConfig.getParameter<uint32_t>("numberOfParameters")),
133  nEvents_(iConfig.getUntrackedParameter<uint32_t>("nEvents"))
134 {
135  if (npars_ != args_.size())
136  throw cms::Exception("ExternalLHEProducer") << "Problem with configuration: " << args_.size() << " script arguments given, expected " << npars_;
137  produces<LHEXMLStringProduct, edm::InRun>("LHEScriptOutput");
138 
139  produces<LHEEventProduct>();
140  produces<LHERunInfoProduct, edm::InRun>();
141 }
T getParameter(std::string const &) const
T getUntrackedParameter(std::string const &, T const &) const
std::vector< std::string > args_
ExternalLHEProducer::~ExternalLHEProducer ( )

Definition at line 144 of file ExternalLHEProducer.cc.

145 {
146 }

Member Function Documentation

void ExternalLHEProducer::beginJob ( void  )
privatevirtual

Reimplemented from edm::EDProducer.

Definition at line 211 of file ExternalLHEProducer.cc.

212 {
213 }
void ExternalLHEProducer::beginLuminosityBlock ( edm::LuminosityBlock lumi,
edm::EventSetup const &   
)
privatevirtual

Reimplemented from edm::EDProducer.

Definition at line 464 of file ExternalLHEProducer.cc.

465 {
466 }
void ExternalLHEProducer::beginRun ( edm::Run run,
edm::EventSetup const &  es 
)
privatevirtual

Reimplemented from edm::EDProducer.

Definition at line 217 of file ExternalLHEProducer.cc.

References LHERunInfoProduct::addComment(), LHERunInfoProduct::addHeader(), args_, edm::hlt::Exception, executeScript(), edm::Service< T >::isAvailable(), LogDebug, edm::RandomNumberGenerator::mySeed(), nEvents_, nextEvent(), outputFile_, AlCaHLTBitMon_ParallelJobs::p, edm::Run::put(), reader_, runInfo, runInfoLast, runInfoProducts, createPayload::skip, and wasMerged.

218 {
219 
220  // pass the number of events as previous to last argument
221 
222  std::ostringstream eventStream;
223  eventStream << nEvents_;
224  args_.push_back(eventStream.str());
225 
226  // pass the random number generator seed as last argument
227 
229 
230  if ( ! rng.isAvailable()) {
231  throw cms::Exception("Configuration")
232  << "The ExternalLHEProducer module requires the RandomNumberGeneratorService\n"
233  "which is not present in the configuration file. You must add the service\n"
234  "in the configuration file if you want to run ExternalLHEProducer";
235  }
236  std::ostringstream randomStream;
237  randomStream << rng->mySeed();
238  args_.push_back(randomStream.str());
239 
240  for ( unsigned int iArg = 0; iArg < args_.size() ; iArg++ ) {
241  LogDebug("LHEInputArgs") << "arg [" << iArg << "] = " << args_[iArg];
242  }
243 
244  executeScript();
245 
246  //fill LHEXMLProduct (streaming read directly into compressed buffer to save memory)
247  std::auto_ptr<LHEXMLStringProduct> p(new LHEXMLStringProduct);
248  std::ifstream instream(outputFile_);
249  if (!instream) {
250  throw cms::Exception("OutputOpenError") << "Unable to open script output file " << outputFile_ << ".";
251  }
252  instream.seekg (0, instream.end);
253  int insize = instream.tellg();
254  instream.seekg (0, instream.beg);
255  p->fillCompressedContent(instream, 0.25*insize);
256  instream.close();
257  run.put(p, "LHEScriptOutput");
258 
259  // LHE C++ classes translation
260  // (read back uncompressed file from disk in streaming mode again to save memory)
261 
262  std::vector<std::string> infiles(1, outputFile_);
263  unsigned int skip = 0;
264  std::auto_ptr<lhef::LHEReader> thisRead( new lhef::LHEReader(infiles, skip ) );
265  reader_ = thisRead;
266 
267  nextEvent();
268  if (runInfoLast) {
270 
271  std::auto_ptr<LHERunInfoProduct> product(new LHERunInfoProduct(*runInfo->getHEPRUP()));
272  std::for_each(runInfo->getHeaders().begin(),
273  runInfo->getHeaders().end(),
274  boost::bind(&LHERunInfoProduct::addHeader,
275  product.get(), _1));
276  std::for_each(runInfo->getComments().begin(),
277  runInfo->getComments().end(),
278  boost::bind(&LHERunInfoProduct::addComment,
279  product.get(), _1));
280 
281  // keep a copy around in case of merging
282  runInfoProducts.push_back(new LHERunInfoProduct(*product));
283  wasMerged = false;
284 
285  run.put(product);
286 
287  runInfo.reset();
288  }
289 
290 }
#define LogDebug(id)
void addHeader(const Header &header)
std::vector< std::string > args_
std::auto_ptr< lhef::LHEReader > reader_
boost::shared_ptr< lhef::LHERunInfo > runInfoLast
bool isAvailable() const
Definition: Service.h:47
boost::shared_ptr< lhef::LHERunInfo > runInfo
void addComment(const std::string &line)
void put(std::auto_ptr< PROD > product)
Put a new product.
Definition: Run.h:81
boost::ptr_deque< LHERunInfoProduct > runInfoProducts
virtual uint32_t mySeed() const =0
Exists for backward compatibility.
int ExternalLHEProducer::closeDescriptors ( int  preserve)
private

Definition at line 312 of file ExternalLHEProducer.cc.

References dir, and NULL.

Referenced by executeScript().

313 {
314  int maxfd = 1024;
315  int fd;
316 #ifdef __linux__
317  DIR * dir;
318  struct dirent *dp;
319  maxfd = preserve;
320  if ((dir = opendir("/proc/self/fd"))) {
321  errno = 0;
322  while ((dp = readdir (dir)) != NULL) {
323  if ((strcmp(dp->d_name, ".") == 0) || (strcmp(dp->d_name, "..") == 0)) {
324  continue;
325  }
326  if (sscanf(dp->d_name, "%d", &fd) != 1) {
327  //throw cms::Exception("closeDescriptors") << "Found unexpected filename in /proc/self/fd: " << dp->d_name;
328  return -1;
329  }
330  if (fd > maxfd) {
331  maxfd = fd;
332  }
333  }
334  if (errno) {
335  //throw cms::Exception("closeDescriptors") << "Unable to determine the number of fd (errno=" << errno << ", " << strerror(errno) << ").";
336  return errno;
337  }
338  closedir(dir);
339  }
340 #endif
341  // TODO: assert for an unreasonable number of fds?
342  for (fd=3; fd<maxfd+1; fd++) {
343  if (fd != preserve)
344  close(fd);
345  }
346  return 0;
347 }
#define NULL
Definition: scimark2.h:8
dbl *** dir
Definition: mlp_gen.cc:35
void ExternalLHEProducer::endLuminosityBlock ( edm::LuminosityBlock ,
edm::EventSetup const &   
)
privatevirtual

Reimplemented from edm::EDProducer.

Definition at line 470 of file ExternalLHEProducer.cc.

471 {
472 }
void ExternalLHEProducer::endRun ( edm::Run run,
edm::EventSetup const &  es 
)
privatevirtual

Reimplemented from edm::EDProducer.

Definition at line 294 of file ExternalLHEProducer.cc.

References edm::hlt::Exception, outputFile_, edm::Run::put(), reader_, and runInfoProducts.

295 {
296 
297  if (!runInfoProducts.empty()) {
298  std::auto_ptr<LHERunInfoProduct> product(runInfoProducts.pop_front().release());
299  run.put(product);
300  }
301 
302  reader_.reset();
303 
304  if (unlink(outputFile_.c_str())) {
305  throw cms::Exception("OutputDeleteError") << "Unable to delete original script output file " << outputFile_ << " (errno=" << errno << ", " << strerror(errno) << ").";
306  }
307 
308 }
std::auto_ptr< lhef::LHEReader > reader_
void put(std::auto_ptr< PROD > product)
Put a new product.
Definition: Run.h:81
boost::ptr_deque< LHERunInfoProduct > runInfoProducts
void ExternalLHEProducer::executeScript ( )
private

Definition at line 351 of file ExternalLHEProducer.cc.

References dir2webdir::argc, args_, dirstructure::argv, closeDescriptors(), edm::hlt::Exception, i, NULL, evf::utils::pid, pipe::pipe(), SiPixelLorentzAngle_cfi::read, scriptName_, ntuplemaker::status, and TablePrint::write.

Referenced by beginRun().

352 {
353 
354  // Fork a script, wait until it finishes.
355 
356  int rc = 0, rc2 = 0;
357  int filedes[2], fd_flags;
358  unsigned int argc;
359 
360  if (pipe(filedes)) {
361  throw cms::Exception("Unable to create a new pipe");
362  }
363  FileCloseSentry sentry1(filedes[0]), sentry2(filedes[1]);
364 
365  if ((fd_flags = fcntl(filedes[1], F_GETFD, NULL)) == -1) {
366  throw cms::Exception("ExternalLHEProducer") << "Failed to get pipe file descriptor flags (errno=" << rc << ", " << strerror(rc) << ")";
367  }
368  if (fcntl(filedes[1], F_SETFD, fd_flags | FD_CLOEXEC) == -1) {
369  throw cms::Exception("ExternalLHEProducer") << "Failed to set pipe file descriptor flags (errno=" << rc << ", " << strerror(rc) << ")";
370  }
371 
372  argc = 1 + args_.size();
373  // TODO: assert that we have a reasonable number of arguments
374  char **argv = new char *[argc+1];
375  argv[0] = strdup(scriptName_.c_str());
376  for (unsigned int i=1; i<argc; i++) {
377  argv[i] = strdup(args_[i-1].c_str());
378  }
379  argv[argc] = NULL;
380 
381  pid_t pid = fork();
382  if (pid == 0) {
383  // The child process
384  if (!(rc = closeDescriptors(filedes[1]))) {
385  execvp(argv[0], argv); // If execv returns, we have an error.
386  rc = errno;
387  }
388  while ((write(filedes[1], &rc, sizeof(int)) == -1) && (errno == EINTR)) {}
389  _exit(1);
390  }
391 
392  // Free the arg vector ASAP
393  for (unsigned int i=0; i<args_.size()+1; i++) {
394  free(argv[i]);
395  }
396  delete [] argv;
397 
398  if (pid == -1) {
399  throw cms::Exception("ForkException") << "Unable to fork a child (errno=" << errno << ", " << strerror(errno) << ")";
400  }
401 
402  close(filedes[1]);
403  // If the exec succeeds, the read will fail.
404  while (((rc2 = read(filedes[0], &rc, sizeof(int))) == -1) && (errno == EINTR)) { rc2 = 0; }
405  if ((rc2 == sizeof(int)) && rc) {
406  throw cms::Exception("ExternalLHEProducer") << "Failed to execute script (errno=" << rc << ", " << strerror(rc) << ")";
407  }
408  close(filedes[0]);
409 
410  int status = 0;
411  errno = 0;
412  do {
413  if (waitpid(pid, &status, 0) < 0) {
414  if (errno == EINTR) {
415  continue;
416  } else {
417  throw cms::Exception("ExternalLHEProducer") << "Failed to read child status (errno=" << errno << ", " << strerror(errno) << ")";
418  }
419  }
420  if (WIFSIGNALED(status)) {
421  throw cms::Exception("ExternalLHEProducer") << "Child exited due to signal " << WTERMSIG(status) << ".";
422  }
423  if (WIFEXITED(status)) {
424  rc = WEXITSTATUS(status);
425  break;
426  }
427  } while (true);
428  if (rc) {
429  throw cms::Exception("ExternalLHEProducer") << "Child failed with exit code " << rc << ".";
430  }
431 
432 }
int i
Definition: DBlmapReader.cc:9
def pipe
Definition: pipe.py:5
#define NULL
Definition: scimark2.h:8
std::vector< std::string > args_
int closeDescriptors(int preserve)
tuple argc
Definition: dir2webdir.py:41
tuple status
Definition: ntuplemaker.py:245
void ExternalLHEProducer::fillDescriptions ( edm::ConfigurationDescriptions descriptions)
static

Definition at line 476 of file ExternalLHEProducer.cc.

References edm::ParameterSetDescription::add(), edm::ConfigurationDescriptions::addDefault(), edm::ParameterSetDescription::addUntracked(), and edm::ParameterSetDescription::setComment().

476  {
477  //The following says we do not know what parameters are allowed so do no validation
478  // Please change this to state exactly what you do use, even if it is no parameters
480  desc.setComment("Executes an external script and places its output file into an EDM collection");
481 
482  edm::FileInPath thePath;
483  desc.add<edm::FileInPath>("scriptName", thePath);
484  desc.add<std::string>("outputFile", "myoutput");
485  desc.add<std::vector<std::string> >("args");
486  desc.add<uint32_t>("numberOfParameters");
487  desc.addUntracked<uint32_t>("nEvents");
488 
489  descriptions.addDefault(desc);
490 }
ParameterDescriptionBase * addUntracked(U const &iLabel, T const &value)
void setComment(std::string const &value)
void addDefault(ParameterSetDescription const &psetDescription)
ParameterDescriptionBase * add(U const &iLabel, T const &value)
void ExternalLHEProducer::nextEvent ( )
privatevirtual

Definition at line 492 of file ExternalLHEProducer.cc.

References partonLevel, reader_, runInfo, and runInfoLast.

Referenced by beginRun(), and produce().

493 {
494 
495  if (partonLevel)
496  return;
497 
498  partonLevel = reader_->next();
499  if (!partonLevel)
500  return;
501 
502  boost::shared_ptr<lhef::LHERunInfo> runInfoThis = partonLevel->getRunInfo();
503  if (runInfoThis != runInfoLast) {
504  runInfo = runInfoThis;
505  runInfoLast = runInfoThis;
506  }
507 }
boost::shared_ptr< lhef::LHEEvent > partonLevel
std::auto_ptr< lhef::LHEReader > reader_
boost::shared_ptr< lhef::LHERunInfo > runInfoLast
boost::shared_ptr< lhef::LHERunInfo > runInfo
void ExternalLHEProducer::produce ( edm::Event iEvent,
const edm::EventSetup iSetup 
)
privatevirtual

Implements edm::EDProducer.

Definition at line 155 of file ExternalLHEProducer.cc.

References LHEEventProduct::addComment(), LHERunInfoProduct::addComment(), LHERunInfoProduct::addHeader(), LHEEventProduct::addWeight(), nextEvent(), partonLevel, edm::Event::put(), runInfo, runInfoProducts, and wasMerged.

156 {
157  nextEvent();
158  if (!partonLevel)
159  return;
160 
161  std::auto_ptr<LHEEventProduct> product(
162  new LHEEventProduct(*partonLevel->getHEPEUP(),
163  partonLevel->originalXWGTUP())
164  );
165  if (partonLevel->getPDF()) {
166  product->setPDF(*partonLevel->getPDF());
167  }
168  std::for_each(partonLevel->weights().begin(),
169  partonLevel->weights().end(),
170  boost::bind(&LHEEventProduct::addWeight,
171  product.get(), _1));
172  product->setScales(partonLevel->scales());
173  product->setNpLO(partonLevel->npLO());
174  product->setNpNLO(partonLevel->npNLO());
175  std::for_each(partonLevel->getComments().begin(),
176  partonLevel->getComments().end(),
177  boost::bind(&LHEEventProduct::addComment,
178  product.get(), _1));
179 
180  iEvent.put(product);
181 
182  if (runInfo) {
183  std::auto_ptr<LHERunInfoProduct> product(new LHERunInfoProduct(*runInfo->getHEPRUP()));
184  std::for_each(runInfo->getHeaders().begin(),
185  runInfo->getHeaders().end(),
186  boost::bind(&LHERunInfoProduct::addHeader,
187  product.get(), _1));
188  std::for_each(runInfo->getComments().begin(),
189  runInfo->getComments().end(),
190  boost::bind(&LHERunInfoProduct::addComment,
191  product.get(), _1));
192 
193  if (!runInfoProducts.empty()) {
194  runInfoProducts.front().mergeProduct(*product);
195  if (!wasMerged) {
196  runInfoProducts.pop_front();
197  runInfoProducts.push_front(product);
198  wasMerged = true;
199  }
200  }
201 
202  runInfo.reset();
203  }
204 
205  partonLevel.reset();
206  return;
207 }
boost::shared_ptr< lhef::LHEEvent > partonLevel
void addHeader(const Header &header)
void addComment(const std::string &line)
void addWeight(const WGT &wgt)
OrphanHandle< PROD > put(std::auto_ptr< PROD > product)
Put a new product.
Definition: Event.h:85
boost::shared_ptr< lhef::LHERunInfo > runInfo
void addComment(const std::string &line)
boost::ptr_deque< LHERunInfoProduct > runInfoProducts
std::auto_ptr< std::string > ExternalLHEProducer::readOutput ( )
private

Definition at line 436 of file ExternalLHEProducer.cc.

References BUFSIZE, edm::hlt::Exception, n, outputFile_, and SiPixelLorentzAngle_cfi::read.

437 {
438  int fd;
439  ssize_t n;
440  char buf[BUFSIZE];
441 
442  if ((fd = open(outputFile_.c_str(), O_RDONLY)) == -1) {
443  throw cms::Exception("OutputOpenError") << "Unable to open script output file " << outputFile_ << " (errno=" << errno << ", " << strerror(errno) << ").";
444  }
445 
446  std::stringstream ss;
447  while ((n = read(fd, buf, BUFSIZE)) > 0 || (n == -1 && errno == EINTR)) {
448  if (n > 0)
449  ss.write(buf, n);
450  }
451  if (n == -1) {
452  throw cms::Exception("OutputOpenError") << "Unable to read from script output file " << outputFile_ << " (errno=" << errno << ", " << strerror(errno) << ").";
453  }
454 
455  if (unlink(outputFile_.c_str())) {
456  throw cms::Exception("OutputDeleteError") << "Unable to delete original script output file " << outputFile_ << " (errno=" << errno << ", " << strerror(errno) << ").";
457  }
458 
459  return std::auto_ptr<std::string>(new std::string(ss.str()));
460 }
#define BUFSIZE

Member Data Documentation

std::vector<std::string> ExternalLHEProducer::args_
private
uint32_t ExternalLHEProducer::nEvents_
private

Definition at line 93 of file ExternalLHEProducer.cc.

Referenced by beginRun().

uint32_t ExternalLHEProducer::npars_
private

Definition at line 92 of file ExternalLHEProducer.cc.

Referenced by ExternalLHEProducer().

std::string ExternalLHEProducer::outputContents_
private

Definition at line 94 of file ExternalLHEProducer.cc.

std::string ExternalLHEProducer::outputFile_
private

Definition at line 90 of file ExternalLHEProducer.cc.

Referenced by beginRun(), endRun(), and readOutput().

boost::shared_ptr<lhef::LHEEvent> ExternalLHEProducer::partonLevel
private

Definition at line 99 of file ExternalLHEProducer.cc.

Referenced by nextEvent(), and produce().

std::auto_ptr<lhef::LHEReader> ExternalLHEProducer::reader_
private

Definition at line 96 of file ExternalLHEProducer.cc.

Referenced by beginRun(), endRun(), and nextEvent().

boost::shared_ptr<lhef::LHERunInfo> ExternalLHEProducer::runInfo
private

Definition at line 98 of file ExternalLHEProducer.cc.

Referenced by beginRun(), nextEvent(), and produce().

boost::shared_ptr<lhef::LHERunInfo> ExternalLHEProducer::runInfoLast
private

Definition at line 97 of file ExternalLHEProducer.cc.

Referenced by beginRun(), and nextEvent().

boost::ptr_deque<LHERunInfoProduct> ExternalLHEProducer::runInfoProducts
private

Definition at line 100 of file ExternalLHEProducer.cc.

Referenced by beginRun(), endRun(), and produce().

std::string ExternalLHEProducer::scriptName_
private

Definition at line 89 of file ExternalLHEProducer.cc.

Referenced by executeScript().

bool ExternalLHEProducer::wasMerged
private

Definition at line 101 of file ExternalLHEProducer.cc.

Referenced by beginRun(), and produce().