Geant4 11.3.0
Toolkit for the simulation of the passage of particles through matter
Loading...
Searching...
No Matches
G4coutFormatters.cc
Go to the documentation of this file.
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// G4coutFormatters implementation
27//
28// Author: A.Dotti (SLAC), April 2017
29// --------------------------------------------------------------------
30
31#include "G4coutFormatters.hh"
32
33namespace G4coutFormatters
34{
35 // Internal functions and utilites used to setup default formatters
36 namespace
37 {
38 // Split a single string in an array of strings
39 //
40 String_V split(const G4String& input, char separator = '\n')
41 {
42 String_V output;
43 G4String::size_type prev_pos = 0, pos = 0;
44 while((pos = input.find(separator, pos)) != G4String::npos)
45 {
46 // TBR: shouldn't be worse than push_back+move
47 output.emplace_back(input.substr(prev_pos, pos - prev_pos));
48 prev_pos = ++pos;
49 }
50 return output;
51 }
52
53 // Return a syslog style message with input message, type identifies
54 // the type of the message
55 //
56 G4bool transform(G4String& input, const G4String& type)
57 {
58 std::time_t result = std::time(nullptr);
59 std::ostringstream newm;
60#if __GNUC__ >= 5
61 newm << std::put_time(std::localtime(&result), "%d/%b/%Y:%H:%M:%S %z");
62#else
63 std::tm* time_ = std::localtime(&result);
64 newm << time_->tm_mday << "/" << time_->tm_mon << "/" << time_->tm_year;
65 newm << ":" << time_->tm_hour << ":" << time_->tm_min << ":"
66 << time_->tm_sec;
67#endif
68 newm << " " << type << " [";
69 G4String delimiter = "";
70 for(const auto& el : split(input))
71 {
72 if(!el.empty())
73 {
74 newm << delimiter << el;
75 delimiter = "\\n";
76 }
77 }
78 newm << " ]" << G4endl;
79 input = newm.str();
80 return true;
81 }
82
83 // Style used in master thread
84 //
85 G4String masterStyle = "";
86
87 // Modify output to look like syslog messages:
88 // DATE TIME **LOG|ERROR** [ "multi","line","message"]
89 //
90 SetupStyle_f SysLogStyle = [](G4coutDestination* dest) -> G4int {
91 if(dest != nullptr)
92 {
93 dest->AddCoutTransformer(
94 std::bind(&transform, std::placeholders::_1, "INFO"));
95 dest->AddCerrTransformer(
96 std::bind(&transform, std::placeholders::_1, "ERROR"));
97 }
98 return 0;
99 };
100
101 // Bring back destination to original state
102 //
103 SetupStyle_f DefaultStyle = [](G4coutDestination* dest) -> G4int {
104 if(dest != nullptr)
105 {
106 dest->ResetTransformers();
107 }
108 return 0;
109 };
110
111 std::unordered_map<std::string, SetupStyle_f> transformers = {
112 { ID::SYSLOG, SysLogStyle },
113 { ID::DEFAULT, DefaultStyle }
114 };
115 } // namespace
116
117 void SetMasterStyle(const G4String& news) { masterStyle = news; }
118
119 G4String GetMasterStyle() { return masterStyle; }
120
121 void SetupStyleGlobally(const G4String& news)
122 {
123 static G4coutDestination ss;
127 }
128
130 {
131 String_V result;
132 for(const auto& el : transformers)
133 {
134 result.push_back(el.first);
135 }
136 return result;
137 }
138
140 {
141 const auto& handler = transformers.find(style);
142 return (handler != transformers.cend()) ? (handler->second)(dest) : -1;
143 }
144
145 void RegisterNewStyle(const G4String& name, SetupStyle_f& fmt)
146 {
147 if(transformers.find(name) != transformers.cend())
148 {
150 msg << "Format Style with name " << name
151 << " already exists. Replacing existing.";
152 G4Exception("G4coutFormatters::RegisterNewStyle()", "FORMATTER001",
153 JustWarning, msg);
154 }
155 // transformers.insert(std::make_pair(name,fmt));
156 transformers[name] = fmt;
157 }
158} // namespace G4coutFormatters
@ JustWarning
void G4Exception(const char *originOfException, const char *exceptionCode, G4ExceptionSeverity severity, const char *description)
std::ostringstream G4ExceptionDescription
bool G4bool
Definition G4Types.hh:86
int G4int
Definition G4Types.hh:85
#define G4endl
Definition G4ios.hh:67
void G4iosSetDestination(G4coutDestination *sink)
Definition G4ios.cc:297
std::vector< G4String > String_V
void RegisterNewStyle(const G4String &name, SetupStyle_f &formatter)
void SetupStyleGlobally(const G4String &news)
std::function< G4int(G4coutDestination *)> SetupStyle_f
void SetMasterStyle(const G4String &)
G4int HandleStyle(G4coutDestination *dest, const G4String &style)