ECCE @ EIC Software
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
G4coutFormatters.cc
Go to the documentation of this file. Or view the newest version in sPHENIX GitHub for file G4coutFormatters.cc
1 //
2 // ********************************************************************
3 // * License and Disclaimer *
4 // * *
5 // * The Geant4 software is copyright of the Copyright Holders of *
6 // * the Geant4 Collaboration. It is provided under the terms and *
7 // * conditions of the Geant4 Software License, included in the file *
8 // * LICENSE and available at http://cern.ch/geant4/license . These *
9 // * include a list of copyright holders. *
10 // * *
11 // * Neither the authors of this software system, nor their employing *
12 // * institutes,nor the agencies providing financial support for this *
13 // * work make any representation or warranty, express or implied, *
14 // * regarding this software system or assume any liability for its *
15 // * use. Please see the license in the file LICENSE and URL above *
16 // * for the full disclaimer and the limitation of liability. *
17 // * *
18 // * This code implementation is the result of the scientific and *
19 // * technical work of the GEANT4 collaboration. *
20 // * By using, copying, modifying or distributing the software (or *
21 // * any work based on the software) you agree to acknowledge its *
22 // * use in resulting scientific publications, and indicate your *
23 // * acceptance of all terms of the Geant4 Software license. *
24 // ********************************************************************
25 //
26 //
27 // --------------------------------------------------------------------
28 //
29 // G4coutFormatters.cc
30 //
31 // Author: A.Dotti (SLAC), April 2017
32 // --------------------------------------------------------------------
33 
34 #include "G4coutFormatters.hh"
35 
36 namespace G4coutFormatters
37 {
38  // Internal functions and utilites used to setup default formatters
39  namespace
40  {
41  // Split a single string in an array of strings
42  String_V split(const G4String& input, char separator='\n')
43  {
44  String_V output;
45  G4String::size_type prev_pos=0, pos=0;
46  while( (pos=input.find(separator,pos))!=G4String::npos)
47  {
48  G4String substr( input.substr(prev_pos,pos-prev_pos)) ;
49  output.push_back(substr);
50  prev_pos = ++pos;
51  }
52  // output.push_back( input.substr(prev_pos,pos-prev_pos));
53  return output;
54  }
55 
56  // Return a syslog style message with input message, type identifies
57  // the type of the message
58  G4bool transform( G4String& input , const G4String& type)
59  {
60  std::time_t result = std::time(nullptr);
61  std::ostringstream newm;
62 #if __GNUC__ >= 5
63  newm << std::put_time(std::localtime(&result),"%d/%b/%Y:%H:%M:%S %z");
64 #else
65  std::tm* time_ = std::localtime(&result);
66  newm << time_->tm_mday << "/" << time_->tm_mon << "/" << time_->tm_year;
67  newm << ":" << time_->tm_hour << ":"<<time_->tm_min<<":"<<time_->tm_sec;
68 #endif
69  newm<<" "<<type<<" [";
70  G4String delimiter = "";
71  for (const auto& el : split(input) )
72  {
73  if ( !el.empty() )
74  {
75  newm << delimiter << el ;
76  delimiter = "\\n";
77  }
78  }
79  newm<<" ]"<<G4endl;
80  input = newm.str();
81  return true;
82  }
83 
84  // Style used in master thread
85  G4String masterStyle = "";
86 
87  // Modify output to look like syslog messages:
88  // DATE TIME **LOG|ERROR** [ "multi","line","message"]
89  SetupStyle_f SysLogStyle = [](G4coutDestination* dest)->G4int
90  {
91  if ( dest != nullptr )
92  {
93  dest->AddCoutTransformer(std::bind(&transform,std::placeholders::_1,
94  "INFO"));
95  dest->AddCerrTransformer(std::bind(&transform,std::placeholders::_1,
96  "ERROR"));
97  }
98  return 0;
99  };
100 
101  // Bring back destination to original state
102  SetupStyle_f DefaultStyle = [](G4coutDestination* dest)->G4int
103  {
104  if ( dest != nullptr )
105  {
106  dest->ResetTransformers();
107  }
108  return 0;
109  };
110 
111  std::unordered_map<std::string,SetupStyle_f> transformers =
112  {
113  {ID::SYSLOG,SysLogStyle},
114  {ID::DEFAULT,DefaultStyle}
115  };
116  }
117 
118  void SetMasterStyle(const G4String& news )
119  {
120  masterStyle = news;
121  }
122 
124  {
125  return masterStyle;
126  }
127 
128  void SetupStyleGlobally(const G4String& news)
129  {
130  static G4coutDestination ss;
135  }
136 
138  {
139  String_V result;
140  for ( const auto& el : transformers )
141  {
142  result.push_back(el.first);
143  }
144  return result;
145  }
146 
148  {
149  const auto& handler = transformers.find(style);
150  return ( handler != transformers.end() ) ? (handler->second)(dest) : -1;
151  }
152 
154  {
155  if ( transformers.find(name) != transformers.end() )
156  {
158  msg << "Format Style with name " << name
159  << " already exists. Replacing existing.";
160  G4Exception("G4coutFormatters::RegisterNewStyle()",
161  "FORMATTER001", JustWarning, msg);
162  }
163  // transformers.insert(std::make_pair(name,fmt));
164  transformers[name]=fmt;
165  }
166 }