CMS 3D CMS Logo

ConfigurationDescriptions.cc
Go to the documentation of this file.
1 // -*- C++ -*-
2 //
3 // Package: ParameterSet
4 // Class : ConfigurationDescriptions
5 //
6 // Implementation:
7 // <Notes on implementation>
8 //
9 // Original Author: W. David Dagenhart
10 // Created: 17 December 2008
11 //
12 
17 
18 #include "boost/bind.hpp"
19 
20 #include <fstream>
21 #include <iostream>
22 #include <iomanip>
23 #include <sstream>
24 #include <cstring>
25 
26 namespace {
27  void matchLabel(std::pair<std::string, edm::ParameterSetDescription> const& thePair,
28  std::string const& moduleLabel,
29  edm::ParameterSetDescription const*& psetDesc) {
30  if (thePair.first == moduleLabel) {
31  psetDesc = &thePair.second;
32  }
33  }
34 }
35 
36 static const char* const kSource ="Source";
37 static const char* const kService = "Service";
38 static const char* const k_source = "source";
39 
40 namespace edm {
41 
43  baseType_(baseType),
44  defaultDescDefined_(false)
45  { }
46 
48 
49  void
51  { comment_ = value; }
52 
53  void
55  { comment_ = value; }
56 
57  void
59  ParameterSetDescription const& psetDescription) {
60  std::string labelString(label);
61  add(labelString, psetDescription);
62  }
63 
64  void
66  ParameterSetDescription const& psetDescription) {
67 
68  if (0==strcmp(baseType_.c_str(),kSource)) {
69  if (0!=strcmp(label.c_str(),k_source)) {
71  "ConfigurationDescriptions::add, when adding a ParameterSetDescription for a source the label must be \"source\"\n");
72  }
73  if (descriptions_.size() != 0U ||
74  defaultDescDefined_ == true) {
76  "ConfigurationDescriptions::add, for a source only 1 ParameterSetDescription may be added\n");
77  }
78  }
79  else if (0==strcmp(baseType_.c_str(),kService)) {
80  if (descriptions_.size() != 0U ||
81  defaultDescDefined_ == true) {
83  "ConfigurationDescriptions::add, for a service only 1 ParameterSetDescription may be added\n");
84  }
85  }
86 
87  // To minimize the number of copies involved create an empty description first
88  // and push it into the vector. Then perform the copy.
89  std::pair<std::string, ParameterSetDescription> pairWithEmptyDescription;
90  descriptions_.push_back(pairWithEmptyDescription);
91  std::pair<std::string, ParameterSetDescription> & pair = descriptions_.back();
92 
93  pair.first = label;
94  pair.second = psetDescription;
95 
96  }
97 
98  void
100 
101  if (0==strcmp(baseType_.c_str(),kSource) || 0==strcmp(baseType_.c_str(),kService)) {
102  if (descriptions_.size() != 0U ||
103  defaultDescDefined_ == true) {
105  "ConfigurationDescriptions::addDefault, for a source or service only 1 ParameterSetDescription may be added\n");
106  }
107  }
108 
109  defaultDescDefined_ = true;
110  defaultDesc_ = psetDescription;
111 
112  }
113 
116  if (defaultDescDefined_) {
117  return &defaultDesc_;
118  }
119  return 0;
120  }
121 
124 
127 
128 
129  void
131  std::string const& moduleLabel) const {
132 
133  ParameterSetDescription const* psetDesc = 0;
134  for_all(descriptions_, std::bind(&matchLabel,
135  std::placeholders::_1,
136  std::cref(moduleLabel),
137  std::ref(psetDesc)));
138 
139  // If there is a matching label
140  if (psetDesc != 0) {
141  psetDesc->validate(pset);
142  }
143  // Is there an explicit description to be used for a non standard label
144  else if (defaultDescDefined_) {
145  defaultDesc_.validate(pset);
146  }
147  // Otherwise use the first one.
148  else if (descriptions_.size() > 0U) {
149  descriptions_[0].second.validate(pset);
150  }
151  // It is possible for no descriptions to be defined and no validation occurs
152  // for this module ever.
153  }
154 
155  void
157  std::string const& pluginName) const {
158 
160  std::placeholders::_1,
161  std::cref(baseType),
162  std::cref(pluginName)));
163  }
164 
165 
166  void
167  ConfigurationDescriptions::writeCfiForLabel(std::pair<std::string, ParameterSetDescription> const& labelAndDesc,
168  std::string const& baseType,
169  std::string const& pluginName)
170  {
171  if (0 == strcmp(baseType.c_str(),kService) && labelAndDesc.first != pluginName) {
173  "ConfigurationDescriptions::writeCfiForLabel\nFor a service the label and the plugin name must be the same.\n")
174  << "This error probably is caused by an incorrect label being passed\nto the ConfigurationDescriptions::add function earlier.\n"
175  << "plugin name = \"" << pluginName << "\" label name = \"" << labelAndDesc.first << "\"\n";
176  }
177 
178  std::string cfi_filename;
179  if (0 == strcmp(baseType.c_str(),kSource)) {
180  cfi_filename = pluginName + "_cfi.py";
181  }
182  else {
183  cfi_filename = labelAndDesc.first + "_cfi.py";
184  }
185  std::ofstream outFile(cfi_filename.c_str());
186 
187 
188  outFile << "import FWCore.ParameterSet.Config as cms\n\n";
189  outFile << labelAndDesc.first << " = cms." << baseType << "('" << pluginName << "'";
190 
191  bool startWithComma = true;
192  int indentation = 2;
193  labelAndDesc.second.writeCfi(outFile, startWithComma, indentation);
194 
195  outFile << ")\n";
196 
197  outFile.close();
198 
199  if (0 == strcmp(baseType.c_str(),kSource)) {
200  std::cout << pluginName << "\n";
201  }
202  else {
203  std::cout << labelAndDesc.first << "\n";
204  }
205  }
206 
207  void ConfigurationDescriptions::print(std::ostream & os,
208  std::string const& moduleLabel,
209  bool brief,
210  bool printOnlyLabels,
211  size_t lineWidth,
212  int indentation,
213  int iPlugin) const {
214  if (!brief) {
215  if (!comment().empty()) {
216  DocFormatHelper::wrapAndPrintText(os, comment(), indentation, lineWidth);
217  }
218  os << "\n";
219  }
220 
221  if (descriptions_.empty() && !defaultDescDefined_) {
222  char oldFill = os.fill();
223  indentation += DocFormatHelper::offsetModuleLabel();
224  os << std::setfill(' ') << std::setw(indentation) << "";
225  os << "There are no PSet descriptions defined for this plugin.\n";
226  os << std::setfill(' ') << std::setw(indentation) << "";
227  os << "PSets will not be validated and no cfi files will be generated.\n";
228  os << std::setfill(oldFill);
229  if (!brief) os << "\n";
230  return;
231  }
232 
234  indentation += DocFormatHelper::offsetModuleLabel();
235  char oldFill = os.fill();
236  os << std::setfill(' ') << std::setw(indentation) << "";
237  os << "This plugin has not implemented the function which defines its\n";
238  os << std::setfill(' ') << std::setw(indentation) << "";
239  os << "configuration descriptions yet. No descriptions are available.\n";
240  os << std::setfill(' ') << std::setw(indentation) << "";
241  os << "Its PSets will not be validated, and no cfi files will be generated.\n";
242  os << std::setfill(oldFill);
243  if (!brief) os << "\n";
244  return;
245  }
246 
247  if (!brief) {
248  std::stringstream ss;
249  if (defaultDescDefined_) {
250  if (descriptions_.empty()) {
251  ss << "This plugin has only one PSet description. "
252  << "This description is always used to validate configurations. "
253  << "Because this configuration has no label, no cfi files will be generated.";
254  }
255  else {
256  ss << "This plugin has " << (descriptions_.size() + 1U) << " PSet descriptions. "
257  << "The description used to validate a configuration is selected by "
258  << "matching the module labels. If none match, then the last description, "
259  << "which has no label, is selected. "
260  << "A cfi file will be generated for each configuration with a module label.";
261  }
262  }
263  else {
264  if (descriptions_.size() == 1U) {
265  ss << "This plugin has " << descriptions_.size() << " PSet description. "
266  << "This description is always used to validate configurations. "
267  << "The label below is used when generating the cfi file.";
268  }
269  else {
270  ss << "This plugin has " << descriptions_.size() << " PSet descriptions. "
271  << "The description used to validate a configuration is selected by "
272  << "matching the module labels. If none match the first description below is used. "
273  << "The module labels below are also used when generating the cfi files.";
274  }
275  }
276  DocFormatHelper::wrapAndPrintText(os, ss.str(), indentation, lineWidth);
277  os << "\n";
278  }
279 
280  indentation += DocFormatHelper::offsetModuleLabel();
281 
283  counter.iPlugin = iPlugin;
284  counter.iSelectedModule = 0;
285  counter.iModule = 0;
286 
288  this,
289  _1,
290  std::ref(os),
291  std::cref(moduleLabel),
292  brief,
293  printOnlyLabels,
294  lineWidth,
295  indentation,
296  std::ref(counter)));
297 
298  if (defaultDescDefined_) {
299  printForLabel(os,
300  std::string("@default"),
301  defaultDesc_,
302  moduleLabel,
303  brief,
304  printOnlyLabels,
305  lineWidth,
306  indentation,
307  counter);
308  }
309  }
310 
311  void
312  ConfigurationDescriptions::printForLabel(std::pair<std::string, ParameterSetDescription> const& labelAndDesc,
313  std::ostream & os,
314  std::string const& moduleLabel,
315  bool brief,
316  bool printOnlyLabels,
317  size_t lineWidth,
318  int indentation,
319  DescriptionCounter & counter) const
320  {
321  printForLabel(os,
322  labelAndDesc.first,
323  labelAndDesc.second,
324  moduleLabel,
325  brief,
326  printOnlyLabels,
327  lineWidth,
328  indentation,
329  counter);
330  }
331 
332  void
334  std::string const& label,
336  std::string const& moduleLabel,
337  bool brief,
338  bool printOnlyLabels,
339  size_t lineWidth,
340  int indentation,
341  DescriptionCounter & counter) const
342  {
343  ++counter.iModule;
344  if (!moduleLabel.empty() && label != moduleLabel) return;
345  ++counter.iSelectedModule;
346 
347  std::stringstream ss;
348  ss << counter.iPlugin << "." << counter.iSelectedModule;
349  std::string section = ss.str();
350 
351  char oldFill = os.fill();
352  os << std::setfill(' ') << std::setw(indentation) << "" << std::setfill(oldFill);
353  os << section << " ";
354  if (label == std::string("@default")) {
355  os << "description without a module label\n";
356  }
357  else {
358  if (!brief) {
359  if (0 == strcmp(baseType_.c_str(),kSource) || 0 == strcmp(baseType_.c_str(),kService)) {
360  os << "label: ";
361  }
362  else {
363  os << "module label: ";
364  }
365  }
366  os << label << "\n";
367  }
368 
369  if (!brief) {
370  if (!description.comment().empty()) {
371  DocFormatHelper::wrapAndPrintText(os, description.comment(), indentation, lineWidth - indentation);
372  }
373  os << "\n";
374  }
375  if (printOnlyLabels) return;
376 
377  DocFormatHelper dfh;
378  dfh.setBrief(brief);
379  dfh.setLineWidth(lineWidth);
381  dfh.setSection(section);
383 
384  description.print(os, dfh);
385  }
386 }
void writeCfis(std::string const &baseType, std::string const &pluginName) const
void printForLabel(std::pair< std::string, ParameterSetDescription > const &labelAndDesc, std::ostream &os, std::string const &moduleLabel, bool brief, bool printOnlyLabels, size_t lineWidth, int indentationn, DescriptionCounter &counter) const
static const char *const kService
void validate(ParameterSet &pset) const
static void writeCfiForLabel(std::pair< std::string, ParameterSetDescription > const &labelAndDesc, std::string const &baseType, std::string const &pluginName)
static void wrapAndPrintText(std::ostream &os, std::string const &text, size_t indent, size_t suggestedWidth)
ParameterSetDescription * defaultDescription()
Returns 0 if no default has been assigned.
static const char *const kSource
ConfigurationDescriptions(std::string const &baseType)
Func for_all(ForwardSequence &s, Func f)
wrapper for std::for_each
Definition: Algorithms.h:16
static int offsetModuleLabel()
void addDefault(ParameterSetDescription const &psetDescription)
void setBrief(bool value)
std::vector< std::pair< std::string, ParameterSetDescription > > descriptions_
void print(std::ostream &os, DocFormatHelper &dfh) const
Definition: value.py:1
void setComment(std::string const &value)
void add(std::string const &label, ParameterSetDescription const &psetDescription)
HLT enums.
static std::atomic< unsigned int > counter
void print(std::ostream &os, std::string const &moduleLabel, bool brief, bool printOnlyLabels, size_t lineWidth, int indentation, int iPlugin) const
void validate(ParameterSet &pset, std::string const &moduleLabel) const
std::string const & comment() const
std::string const & comment() const
static const char *const k_source
static int offsetTopLevelPSet()
void setSection(std::string const &value)
std::vector< std::pair< std::string, ParameterSetDescription > >::iterator iterator
void setParent(DescriptionParent value)
void setIndentation(int value)
void setLineWidth(size_t value)