CMS 3D CMS Logo

 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Groups Pages
FriendlyName.cc
Go to the documentation of this file.
1 /*
2  * friendlyName.cpp
3  * CMSSW
4  *
5  * Created by Chris Jones on 2/24/06.
6  *
7  */
8 #include <string>
9 #include <regex>
10 #include <iostream>
11 #include <cassert>
12 #include "tbb/concurrent_unordered_map.h"
13 
14 //NOTE: This should probably be rewritten so that we break the class name into a tree where the template arguments are the node. On the way down the tree
15 // we look for '<' or ',' and on the way up (caused by finding a '>') we can apply the transformation to the output string based on the class name for the
16 // templated class. Up front we'd register a class name to a transformation function (which would probably take a std::vector<std::string> which holds
17 // the results of the node transformations)
18 
19 namespace {
20  constexpr bool debug = false;
21  std::string prefix; // used only if debug == true
22 } // namespace
23 
24 namespace edm {
25  namespace friendlyname {
26  static std::regex const reBeginSpace("^ +");
27  static std::regex const reEndSpace(" +$");
28  static std::regex const reAllSpaces(" +");
29  static std::regex const reColons("::");
30  static std::regex const reComma(",");
31  static std::regex const reTemplateArgs("[^<]*<(.*)>$");
32  static std::regex const rePointer("\\*");
33  static std::regex const reArray("\\[\\]");
34  static std::regex const reUniquePtrDeleter("^std::unique_ptr< *(.*), *std::default_delete<\\1> *>");
35  static std::regex const reUniquePtr("^std::unique_ptr");
36  static std::string const emptyString("");
37 
38  std::string handleNamespaces(std::string const& iIn) { return std::regex_replace(iIn, reColons, emptyString); }
39 
41  return std::regex_replace(std::regex_replace(iIn, reBeginSpace, emptyString), reEndSpace, emptyString);
42  }
43 
44  std::string removeAllSpaces(std::string const& iIn) { return std::regex_replace(iIn, reAllSpaces, emptyString); }
45  static std::regex const reWrapper("edm::Wrapper<(.*)>");
46  static std::regex const reString("std::basic_string<char>");
47  static std::regex const reString2("std::string");
48  static std::regex const reString3("std::basic_string<char,std::char_traits<char> >");
49  //The c++11 abi for gcc internally uses a different namespace for standard classes
50  static std::regex const reCXX11("std::__cxx11::");
51  static std::regex const reSorted("edm::SortedCollection<(.*), *edm::StrictWeakOrdering<\\1 *> >");
52  static std::regex const reclangabi("std::__1::");
53  static std::regex const reULongLong("ULong64_t");
54  static std::regex const reLongLong("Long64_t");
55  static std::regex const reUnsigned("unsigned ");
56  static std::regex const reLong("long ");
57  static std::regex const reVector("std::vector");
58  static std::regex const reUnorderedSetHashKeyEqual(
59  "std::unordered_set< *(.*), *std::hash<\\1> *, *std::equal_to<\\1> *>");
60  static std::regex const reUnorderedSetCustomHashKeyEqual(
61  "std::unordered_set< *(.*), *(.*) *, *std::equal_to<\\1> *>");
62  static std::regex const reUnorderedSetHash("std::unordered_set< *(.*), *std::hash<\\1> *>");
63  static std::regex const reUnorderedSet("std::unordered_set");
64  static std::regex const reUnorderedMapHashKeyEqual(
65  "std::unordered_map< *(.*), *(.*), *std::hash<\\1> *, *std::equal_to<\\1> *>");
66  static std::regex const reUnorderedMapCustomHashKeyEqual(
67  "std::unordered_map< *(.*), *(.*), *(.*) *, *std::equal_to<\\1> *>");
68  static std::regex const reUnorderedMapHash("std::unordered_map< *(.*), *(.*), *std::hash<\\1> *>");
69  static std::regex const reUnorderedMap("std::unordered_map");
70  static std::regex const reSharedPtr("std::shared_ptr");
71  static std::regex const reAIKR(
72  ", *edm::helper::AssociationIdenticalKeyReference"); //this is a default so can replaced with empty
73  //force first argument to also be the argument to edm::ClonePolicy so that if OwnVector is within
74  // a template it will not eat all the remaining '>'s
75  static std::regex const reOwnVector("edm::OwnVector<(.*), *edm::ClonePolicy<\\1 *> >");
76 
77  //NOTE: the '?' means make the smallest match. This may lead to problems where the template arguments themselves have commas
78  // but we are using it in the cases where edm::AssociationMap appears multiple times in template arguments
79  static std::regex const reOneToOne("edm::AssociationMap< *edm::OneToOne<(.*?),(.*?), *u[a-z]*> >");
80  static std::regex const reOneToMany("edm::AssociationMap< *edm::OneToMany<(.*?),(.*?), *u[a-z]*> >");
81  static std::regex const reOneToValue("edm::AssociationMap< *edm::OneToValue<(.*?),(.*?), *u[a-z]*> >");
82  static std::regex const reOneToManyWithQuality(
83  "edm::AssociationMap<edm::OneToManyWithQuality<(.*?), *(.*?), *(.*?), *u[a-z]*> >");
84  static std::regex const reToVector("edm::AssociationVector<(.*), *(.*), *edm::Ref.*,.*>");
85  //NOTE: if the item within a clone policy is a template, this substitution will probably fail
86  static std::regex const reToRangeMap("edm::RangeMap< *(.*), *(.*), *edm::ClonePolicy<([^>]*)> >");
87  //NOTE: If container is a template with one argument which is its 'type' then can simplify name
88  static std::regex const reToRefs1(
89  "edm::RefVector< *(.*)< *(.*) *>, *\\2 *, *edm::refhelper::FindUsingAdvance< *\\1< *\\2 *> *, *\\2 *> *>");
90  static std::regex const reToRefs2(
91  "edm::RefVector< *(.*) *, *(.*) *, *edm::refhelper::FindUsingAdvance< *\\1, *\\2 *> *>");
92  static std::regex const reToRefsAssoc(
93  "edm::RefVector< *Association(.*) *, *edm::helper(.*), *Association(.*)::Find>");
94 
96  using std::regex;
97  using std::regex_replace;
98  std::string name = regex_replace(iIn, reWrapper, "$1");
99  name = regex_replace(name, rePointer, "ptr");
100  name = regex_replace(name, reArray, "As");
101  name = regex_replace(name, reAIKR, "");
102  name = regex_replace(name, reclangabi, "std::");
103  name = regex_replace(name, reCXX11, "std::");
104  name = regex_replace(name, reString, "String");
105  name = regex_replace(name, reString2, "String");
106  name = regex_replace(name, reString3, "String");
107  name = regex_replace(name, reSorted, "sSorted<$1>");
108  name = regex_replace(name, reULongLong, "ull");
109  name = regex_replace(name, reLongLong, "ll");
110  name = regex_replace(name, reUnsigned, "u");
111  name = regex_replace(name, reLong, "l");
112  name = regex_replace(name, reVector, "s");
113  name = regex_replace(name, reSharedPtr, "SharedPtr");
114  name = regex_replace(name, reOwnVector, "sOwned<$1>");
115  name = regex_replace(name, reToVector, "AssociationVector<$1,To,$2>");
116  name = regex_replace(name, reOneToOne, "Association<$1,ToOne,$2>");
117  name = regex_replace(name, reOneToMany, "Association<$1,ToMany,$2>");
118  name = regex_replace(name, reOneToValue, "Association<$1,ToValue,$2>");
119  name = regex_replace(name, reOneToManyWithQuality, "Association<$1,ToMany,$2,WithQuantity,$3>");
120  name = regex_replace(name, reToRangeMap, "RangeMap<$1,$2>");
121  name = regex_replace(name, reToRefs1, "Refs<$1<$2>>");
122  name = regex_replace(name, reToRefs2, "Refs<$1,$2>");
123  name = regex_replace(name, reToRefsAssoc, "Refs<Association$1>");
124  //std::cout <<"standardRenames '"<<name<<"'"<<std::endl;
125  return name;
126  }
127 
130  using namespace std;
131  std::string result = removeExtraSpaces(iFullName);
132 
133  // temporarily remove leading const
134  std::string leadingConst;
135  if (std::string_view{result}.substr(0, 5) == "const") {
136  leadingConst = "const";
137  result = removeExtraSpaces(result.substr(5));
138  }
139 
140  if constexpr (debug) {
141  std::cout << prefix << "subFriendlyName iFullName " << iFullName << " result " << result << std::endl;
142  }
143  // Handle unique_ptr, which may contain the deleter (but handle only std::default_delete)
144  {
145  auto result2 =
146  regex_replace(result, reUniquePtrDeleter, "UniquePtr<$1>", std::regex_constants::format_first_only);
147  if (result2 == result) {
148  result2 = regex_replace(result, reUniquePtr, "UniquePtr", std::regex_constants::format_first_only);
149  }
150  result = std::move(result2);
151  }
152  // insert the leading const back if it was there
153  result = leadingConst + result;
154  // Handle unordered_set, which may contain a hash and an an equal for the key
155  {
156  auto result2 =
157  regex_replace(result, reUnorderedSetHashKeyEqual, "stduset<$1>", std::regex_constants::format_first_only);
158  if (result2 == result) {
159  result2 = regex_replace(
160  result, reUnorderedSetCustomHashKeyEqual, "stduset<$1, $2>", std::regex_constants::format_first_only);
161  }
162  if (result2 == result) {
163  result2 = regex_replace(result, reUnorderedSetHash, "stduset<$1>", std::regex_constants::format_first_only);
164  }
165  if (result2 == result) {
166  result2 = regex_replace(result, reUnorderedSet, "stduset", std::regex_constants::format_first_only);
167  }
168  result = std::move(result2);
169  }
170  // Handle unordered_map, which may contain a hash and an an equal for the key
171  {
172  auto result2 = regex_replace(
173  result, reUnorderedMapHashKeyEqual, "stdumap<$1, $2>", std::regex_constants::format_first_only);
174  if (result2 == result) {
175  result2 = regex_replace(
176  result, reUnorderedMapCustomHashKeyEqual, "stdumap<$1, $2, $3>", std::regex_constants::format_first_only);
177  }
178  if (result2 == result) {
179  result2 =
180  regex_replace(result, reUnorderedMapHash, "stdumap<$1, $2>", std::regex_constants::format_first_only);
181  }
182  if (result2 == result) {
183  result2 = regex_replace(result, reUnorderedMap, "stdumap", std::regex_constants::format_first_only);
184  }
185  result = std::move(result2);
186  }
187  if (smatch theMatch; regex_match(result, theMatch, reTemplateArgs)) {
188  //std::cout <<"found match \""<<theMatch.str(1) <<"\"" <<std::endl;
189  //static regex const templateClosing(">$");
190  //std::string aMatch = regex_replace(theMatch.str(1),templateClosing,"");
191  std::string aMatch = theMatch.str(1);
192  if constexpr (debug) {
193  prefix += " ";
194  }
195  std::string theSub = handleTemplateArguments(aMatch);
196  if constexpr (debug) {
197  prefix.pop_back();
198  prefix.pop_back();
199  std::cout << prefix << " aMatch " << aMatch << " theSub " << theSub << std::endl;
200  }
201  regex const eMatch(std::string("(^[^<]*)<") + aMatch + ">");
202  result = regex_replace(result, eMatch, theSub + "$1");
203  }
204  return removeAllSpaces(result);
205  }
206 
208  using namespace std;
210  if constexpr (debug) {
211  std::cout << prefix << "handleTemplateArguments " << iIn << " removeExtraSpaces " << result << std::endl;
212  }
213 
214  // Trick to have every full class name to end with comma to
215  // avoid treating the end as a special case
216  result += ",";
217 
218  std::string result2;
219  result2.reserve(iIn.size());
220  unsigned int openTemplate = 0;
221  bool hadTemplate = false;
222  size_t begin = 0;
223  for (size_t i = 0, size = result.size(); i < size; ++i) {
224  if (result[i] == '<') {
225  ++openTemplate;
226  hadTemplate = true;
227  continue;
228  } else if (result[i] == '>') {
229  --openTemplate;
230  }
231  // If we are not within the template arguments of a class template
232  // - encountering comma means that we are within a template
233  // argument of some other class template, and we've reached
234  // a point when we should translate the argument class name
235  // - encountering colon, but only if the class name so far
236  // itself was a template, we've reached a point when we
237  // should translate the class name
238  if (const bool hasComma = result[i] == ',', hasColon = hadTemplate and result[i] == ':';
239  openTemplate == 0 and (hasComma or hasColon)) {
240  std::string templateClass = result.substr(begin, i - begin);
241  if constexpr (debug) {
242  std::cout << prefix << " templateClass " << templateClass << std::endl;
243  }
244  if (hadTemplate) {
245  if constexpr (debug) {
246  prefix += " ";
247  }
248  std::string friendlierName = subFriendlyName(templateClass);
249  if constexpr (debug) {
250  prefix.pop_back();
251  prefix.pop_back();
252  std::cout << prefix << " friendlierName " << friendlierName << std::endl;
253  }
254  result2 += friendlierName;
255  } else {
256  result2 += templateClass;
257  }
258  if constexpr (debug) {
259  std::cout << prefix << " result2 " << result2 << std::endl;
260  }
261  // reset counters
262  hadTemplate = false;
263  begin = i + 1;
264  // With colon we need to eat the second colon as well
265  if (hasColon) {
266  assert(result[begin] == ':');
267  ++begin;
268  }
269  }
270  }
271 
272  result = regex_replace(result2, reComma, "");
273  if constexpr (debug) {
274  std::cout << prefix << " reComma " << result << std::endl;
275  }
276  return result;
277  }
279  if constexpr (debug) {
280  std::cout << "\nfriendlyName for " << iFullName << std::endl;
281  prefix = " ";
282  }
283  typedef tbb::concurrent_unordered_map<std::string, std::string> Map;
284  static Map s_fillToFriendlyName;
285  auto itFound = s_fillToFriendlyName.find(iFullName);
286  if (s_fillToFriendlyName.end() == itFound) {
287  itFound = s_fillToFriendlyName
288  .insert(Map::value_type(iFullName, handleNamespaces(subFriendlyName(standardRenames(iFullName)))))
289  .first;
290  }
291  if constexpr (debug) {
292  std::cout << "result " << itFound->second << std::endl;
293  }
294  return itFound->second;
295  }
296  } // namespace friendlyname
297 } // namespace edm
static std::regex const reToRefs1("edm::RefVector< *(.*)< *(.*) *>, *\\2 *, *edm::refhelper::FindUsingAdvance< *\\1< *\\2 *> *, *\\2 *> *>")
static std::regex const reEndSpace(" +$")
static std::regex const reToRangeMap("edm::RangeMap< *(.*), *(.*), *edm::ClonePolicy<([^>]*)> >")
static std::regex const reUnorderedMap("std::unordered_map")
static std::regex const reCXX11("std::__cxx11::")
static std::regex const reUnorderedMapHash("std::unordered_map< *(.*), *(.*), *std::hash<\\1> *>")
static std::regex const reAIKR(", *edm::helper::AssociationIdenticalKeyReference")
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::EventIDconst &, edm::Timestampconst & > We also list in braces which AR_WATCH_USING_METHOD_ is used for those or
Definition: Activities.doc:12
static std::regex const reString3("std::basic_string<char,std::char_traits<char> >")
static std::regex const reUnsigned("unsigned ")
std::string removeAllSpaces(std::string const &iIn)
Definition: FriendlyName.cc:44
std::string subFriendlyName(std::string const &iFullName)
static std::regex const reSharedPtr("std::shared_ptr")
static std::regex const rePointer("\\*")
static std::regex const reOneToManyWithQuality("edm::AssociationMap<edm::OneToManyWithQuality<(.*?), *(.*?), *(.*?), *u[a-z]*> >")
static std::regex const reUniquePtrDeleter("^std::unique_ptr< *(.*), *std::default_delete<\\1> *>")
static std::regex const reToVector("edm::AssociationVector<(.*), *(.*), *edm::Ref.*,.*>")
assert(be >=bs)
static std::regex const reLong("long ")
static std::regex const reOneToMany("edm::AssociationMap< *edm::OneToMany<(.*?),(.*?), *u[a-z]*> >")
static std::regex const reOwnVector("edm::OwnVector<(.*), *edm::ClonePolicy<\\1 *> >")
tuple result
Definition: mps_fire.py:311
static std::regex const reSorted("edm::SortedCollection<(.*), *edm::StrictWeakOrdering<\\1 *> >")
static std::regex const reLongLong("Long64_t")
static std::regex const reComma(",")
std::string friendlyName(std::string const &iFullName)
static std::regex const reUnorderedSetCustomHashKeyEqual("std::unordered_set< *(.*), *(.*) *, *std::equal_to<\\1> *>")
def move
Definition: eostools.py:511
static std::regex const reOneToOne("edm::AssociationMap< *edm::OneToOne<(.*?),(.*?), *u[a-z]*> >")
std::string handleNamespaces(std::string const &iIn)
Definition: FriendlyName.cc:38
static std::regex const reWrapper("edm::Wrapper<(.*)>")
static std::regex const reUnorderedSet("std::unordered_set")
static std::regex const reArray("\\[\\]")
static std::regex const reTemplateArgs("[^<]*<(.*)>$")
static std::regex const reToRefsAssoc("edm::RefVector< *Association(.*) *, *edm::helper(.*), *Association(.*)::Find>")
static std::regex const reULongLong("ULong64_t")
static std::regex const reVector("std::vector")
#define debug
Definition: HDRShower.cc:19
std::string standardRenames(std::string const &iIn)
Definition: FriendlyName.cc:95
static std::regex const reColons("::")
std::string handleTemplateArguments(std::string const &)
static std::regex const reUnorderedMapHashKeyEqual("std::unordered_map< *(.*), *(.*), *std::hash<\\1> *, *std::equal_to<\\1> *>")
static std::regex const reUnorderedSetHash("std::unordered_set< *(.*), *std::hash<\\1> *>")
static std::string const emptyString("")
static std::regex const reUnorderedSetHashKeyEqual("std::unordered_set< *(.*), *std::hash<\\1> *, *std::equal_to<\\1> *>")
static std::regex const reBeginSpace("^ +")
static std::regex const reUniquePtr("^std::unique_ptr")
tuple cout
Definition: gather_cfg.py:144
static std::regex const reUnorderedMapCustomHashKeyEqual("std::unordered_map< *(.*), *(.*), *(.*) *, *std::equal_to<\\1> *>")
static std::regex const reclangabi("std::__1::")
static std::regex const reString2("std::string")
static std::regex const reString("std::basic_string<char>")
static std::regex const reAllSpaces(" +")
tuple size
Write out results.
static std::regex const reOneToValue("edm::AssociationMap< *edm::OneToValue<(.*?),(.*?), *u[a-z]*> >")
static std::regex const reToRefs2("edm::RefVector< *(.*) *, *(.*) *, *edm::refhelper::FindUsingAdvance< *\\1, *\\2 *> *>")
std::string removeExtraSpaces(std::string const &iIn)
Definition: FriendlyName.cc:40