Arcane  v3.14.10.0
Documentation développeur
Chargement...
Recherche...
Aucune correspondance
TraceMngPolicy.cc
1// -*- tab-width: 2; indent-tabs-mode: nil; coding: utf-8-with-signature -*-
2//-----------------------------------------------------------------------------
3// Copyright 2000-2022 CEA (www.cea.fr) IFPEN (www.ifpenergiesnouvelles.com)
4// See the top-level COPYRIGHT file for details.
5// SPDX-License-Identifier: Apache-2.0
6//-----------------------------------------------------------------------------
7/*---------------------------------------------------------------------------*/
8/* TraceMngPolicy.cc (C) 2000-2019 */
9/* */
10/* Politique de configuration des gestionnaires de trace. */
11/*---------------------------------------------------------------------------*/
12/*---------------------------------------------------------------------------*/
13
14#include "arccore/base/ReferenceCounter.h"
15
16#include "arcane/utils/ITraceMng.h"
17#include "arcane/utils/StringBuilder.h"
18#include "arcane/utils/Iostream.h"
19#include "arcane/utils/ScopedPtr.h"
20#include "arcane/utils/PlatformUtils.h"
21#include "arcane/utils/String.h"
22#include "arcane/utils/TraceClassConfig.h"
23#include "arcane/utils/Array.h"
24#include "arcane/utils/ValueConvert.h"
25#include "arcane/utils/Iterator.h"
26#include "arcane/utils/ITraceMngPolicy.h"
27
28#include "arcane/XmlNode.h"
29#include "arcane/XmlNodeList.h"
30#include "arcane/IApplication.h"
31#include "arcane/IXmlDocumentHolder.h"
32
33#include <map>
34#include <mutex>
35#include <algorithm>
36
37/*---------------------------------------------------------------------------*/
38/*---------------------------------------------------------------------------*/
39
40namespace Arcane
41{
42
43/*---------------------------------------------------------------------------*/
44/*---------------------------------------------------------------------------*/
53: public ITraceMngPolicy
54{
55 public:
57 : m_application(app), m_is_parallel(false), m_is_debug(false),
58 m_is_master_has_output_file(false),
59 m_stdout_verbosity_level(Trace::UNSPECIFIED_VERBOSITY_LEVEL),
60 m_verbosity_level(Trace::UNSPECIFIED_VERBOSITY_LEVEL),
61 m_is_parallel_output(false)
62 {
63 m_default_config_doc = IXmlDocumentHolder::createNull();
64 m_output_file_prefix = platform::getEnvironmentVariable("ARCANE_PARALLEL_OUTPUT_PREFIX");
65 }
66
68 {
69 }
70
71 void build() override {}
72 void initializeTraceMng(ITraceMng* trace,Int32 rank) override;
75 void setIsParallel(bool v) override { m_is_parallel = v; }
76 bool isParallel() const override { return m_is_parallel; }
77 void setIsDebug(bool v) override { m_is_debug = v; }
78 bool isDebug() const override { return m_is_debug; }
79 void setIsParallelOutput(bool v) override { m_is_parallel_output = v; }
80 bool isParallelOutput() const override { return m_is_parallel_output; }
81 void setStandardOutputVerbosityLevel(Int32 level) override { m_stdout_verbosity_level = level; }
82 Int32 standardOutputVerbosityLevel() const override { return m_stdout_verbosity_level; }
83 void setVerbosityLevel(Int32 level) override { m_verbosity_level = level; }
84 Int32 verbosityLevel() const override { return m_verbosity_level; }
85 void setIsMasterHasOutputFile(bool active) override { m_is_master_has_output_file = active; }
86 bool isMasterHasOutputFile() const override { return m_is_master_has_output_file; }
87 void setDefaultVerboseLevel(ITraceMng* trace,Int32 minimal_level) override;
88 void setDefaultClassConfigXmlBuffer(ByteConstSpan bytes) override;
89
90 private:
91
92 IApplication* m_application;
93 bool m_is_parallel;
94 bool m_is_debug;
95 bool m_is_master_has_output_file;
96 Int32 m_stdout_verbosity_level;
97 Int32 m_verbosity_level;
98 std::map<String,Arccore::ReferenceCounter<ITraceStream>> m_output_files;
99 String m_output_file_prefix;
100 bool m_is_parallel_output;
101 ScopedPtrT<IXmlDocumentHolder> m_default_config_doc;
102 std::mutex m_init_mutex;
103 std::mutex m_getfile_mutex;
104
105 private:
106
107 ITraceStream* _getFile(const String& rank);
108 void _initializeTraceClasses(ITraceMng* trace);
109 void _setAllTraceClassConfig(ITraceMng* trace,ByteConstArrayView bytes,bool do_log);
110 void _setAllTraceClassConfig(ITraceMng* trace,XmlNode root_element,bool do_log);
111 void _setAllTraceClassConfig(ITraceMng* trace,IXmlDocumentHolder* doc,bool do_log);
112 void _initializeTraceMng(ITraceMng* trace,bool is_master,const String& rank_str);
113};
114
115/*---------------------------------------------------------------------------*/
116/*---------------------------------------------------------------------------*/
117
118extern "C++" ARCANE_IMPL_EXPORT ITraceMngPolicy*
119arcaneCreateTraceMngPolicy(IApplication* app)
120{
121 ITraceMngPolicy* itmp = new TraceMngPolicy(app);
122 itmp->build();
123 return itmp;
124}
125
126/*---------------------------------------------------------------------------*/
127/*---------------------------------------------------------------------------*/
128
130initializeTraceMng(ITraceMng* trace,Int32 rank)
131{
132 _initializeTraceMng(trace,rank==0,String::fromNumber(rank));
133}
134
135/*---------------------------------------------------------------------------*/
136/*---------------------------------------------------------------------------*/
137
138void TraceMngPolicy::
139_initializeTraceMng(ITraceMng* trace,bool is_master,const String& rank_str)
140{
141 bool is_output_file = false;
142 {
145 trace_id += ",";
146 trace_id += platform::getHostName();
147 trace->setTraceId(trace_id.toString());
148 }
149 // Par défaut si rien n'est spécifié, seul le proc maitre sort les infos.
150 bool is_info_disabled = !is_master;
151 if (m_is_parallel_output){
152 is_info_disabled = false;
153 is_output_file = true;
154 }
155 if (is_master && m_is_master_has_output_file)
156 is_output_file = true;
157
158 trace->setInfoActivated(!is_info_disabled);
159
160 if (is_output_file){
161 ITraceStream* ofile = _getFile(rank_str);
162 trace->setRedirectStream(ofile);
163 }
164
165 _initializeTraceClasses(trace);
166 trace->setMaster(is_master);
167 trace->finishInitialize();
168}
169
170/*---------------------------------------------------------------------------*/
171/*---------------------------------------------------------------------------*/
172
175{
176 _initializeTraceMng(trace,false,file_suffix);
177 if (parent_trace){
178 trace->setVerbosityLevel(parent_trace->verbosityLevel());
179 trace->setStandardOutputVerbosityLevel(parent_trace->standardOutputVerbosityLevel());
180 }
181}
182
183/*---------------------------------------------------------------------------*/
184/*---------------------------------------------------------------------------*/
185
188{
189 if (m_verbosity_level!=Trace::UNSPECIFIED_VERBOSITY_LEVEL){
190 Int32 level = m_verbosity_level;
191 if (minimal_level!=Trace::UNSPECIFIED_VERBOSITY_LEVEL)
192 level = std::max(level,minimal_level);
193 trace->setVerbosityLevel(level);
194 }
195 if (m_stdout_verbosity_level!=Trace::UNSPECIFIED_VERBOSITY_LEVEL){
196 Int32 level = m_stdout_verbosity_level;
197 if (minimal_level!=Trace::UNSPECIFIED_VERBOSITY_LEVEL)
198 level = std::max(level,minimal_level);
200 }
201}
202
203/*---------------------------------------------------------------------------*/
204/*---------------------------------------------------------------------------*/
205
208{
209 _setAllTraceClassConfig(trace,bytes,false);
210}
211
212/*---------------------------------------------------------------------------*/
213/*---------------------------------------------------------------------------*/
214
215void TraceMngPolicy::
216setDefaultClassConfigXmlBuffer(ByteConstSpan bytes)
217{
218 if (bytes.empty()){
219 m_default_config_doc = IXmlDocumentHolder::createNull();
220 return;
221 }
222
223 ITraceMng* tm = m_application->traceMng();
224 m_default_config_doc = IXmlDocumentHolder::loadFromBuffer(bytes,String(),tm);
225}
226
227/*---------------------------------------------------------------------------*/
228/*---------------------------------------------------------------------------*/
229
230ITraceStream* TraceMngPolicy::
231_getFile(const String& rank)
232{
233 std::lock_guard<std::mutex> guard(m_getfile_mutex);
234
235 auto i = m_output_files.find(rank);
236 if (i!=m_output_files.end())
237 return i->second.get();
238
239 StringBuilder buf(m_output_file_prefix);
240 if (!m_output_file_prefix.null()) {
241 buf += "/";
242 }
243 buf += "output";
244 buf += rank;
245 String bufstr = buf.toString();
246
247 ReferenceCounter<ITraceStream> stream(ITraceStream::createFileStream(bufstr));
248 m_output_files.insert(std::make_pair(rank,stream));
249 return stream.get();
250}
251
252/*---------------------------------------------------------------------------*/
253/*---------------------------------------------------------------------------*/
254
255void TraceMngPolicy::
256_initializeTraceClasses(ITraceMng* trace)
257{
258 _setAllTraceClassConfig(trace,m_default_config_doc.get(),true);
259}
260
261/*---------------------------------------------------------------------------*/
262/*---------------------------------------------------------------------------*/
263
264void TraceMngPolicy::
265_setAllTraceClassConfig(ITraceMng* trace,ByteConstArrayView bytes,bool do_log)
266{
267 ScopedPtrT<IXmlDocumentHolder> config_doc;
268 if (!bytes.empty()){
269 // Trace pour afficher les informations lors de la lecture.
270 // Ne pas confondre avec \a trace passé en argument
271 ITraceMng* print_tm = m_application->traceMng();
272 config_doc = IXmlDocumentHolder::loadFromBuffer(bytes,String(),print_tm);
273 }
274 _setAllTraceClassConfig(trace,config_doc.get(),do_log);
275}
276
277/*---------------------------------------------------------------------------*/
278/*---------------------------------------------------------------------------*/
279
280void TraceMngPolicy::
281_setAllTraceClassConfig(ITraceMng* trace,IXmlDocumentHolder* doc,bool do_log)
282{
283 // Il faut toujours appeler _setAllTraceClassConfig même si on n'a pas
284 // d'élément racine sinon l'initialisation par défaut est incorrecte.
285 XmlNode root_element;
286 if (doc){
287 XmlNode document_node = m_default_config_doc->documentNode();
288 if (!document_node.null())
289 root_element = document_node.documentElement();
290 }
291 _setAllTraceClassConfig(trace,root_element,do_log);
292}
293
294/*---------------------------------------------------------------------------*/
295/*---------------------------------------------------------------------------*/
296
297void TraceMngPolicy::
298_setAllTraceClassConfig(ITraceMng* trace,XmlNode root_element,bool do_log)
299{
300 if (do_log)
301 trace->logdate() << "Reading trace classes";
302
303 trace->removeAllClassConfig();
304 bool is_info_activated = trace->isInfoActivated();
305 Trace::eDebugLevel debug_level = Trace::Medium;
306 // Désactive les infos de debug si on ne sort pas sur un fichier
307 // et que les infos sont désactivées. Cela évite que tous les PE écrivent
308 // les infos de débug dans la sortie standard.
309 if (!is_info_activated && !m_is_parallel_output)
310 debug_level = Trace::None;
311 TraceClassConfig medium_cc(is_info_activated,true,debug_level);
312 trace->setClassConfig("*",medium_cc);
313 if (root_element.null()){
314 if (do_log)
315 trace->log() << "No user configuration";
316 return;
317 }
318
319 XmlNodeList children = root_element.child("traces").children("trace-class");
320 String ustr_name("name");
321 String ustr_info("info");
322 String ustr_pinfo("parallel-info");
323 String ustr_debug("debug");
324 String ustr_true("true");
325 String ustr_none("none");
326 String ustr_lowest("lowest");
327 String ustr_low("low");
328 String ustr_medium("medium");
329 String ustr_high("high");
330 String ustr_highest("highest");
331 String ustr_star("*");
332 String ustr_print_class_name("print-class-name");
333 String ustr_print_elapsed_time("print-elapsed-time");
334
335 for( const auto& xnode : children ){
336 String module_name = xnode.attrValue(ustr_name);
337 String activate_str = xnode.attrValue(ustr_info);
338 String parallel_activate_str = xnode.attrValue(ustr_pinfo);
339 String dbg_lvl_str = xnode.attrValue(ustr_debug);
340 String print_class_name_str = xnode.attrValue(ustr_print_class_name);
341 String print_elapsed_time_str = xnode.attrValue(ustr_print_elapsed_time);
342 if (module_name.null())
343 continue;
344 TraceClassConfig def_config = trace->classConfig("*");
345 bool is_activate = def_config.isActivated();
346 builtInGetValue(is_activate,activate_str);
347 bool is_parallel_activate = is_activate;
348 // Si \a disable_info vaut true, désactive les messages d'info sauf si
349 // \e parallel-info vaut \a true
350 if (!is_info_activated){
351 is_activate = false;
352 if (parallel_activate_str==ustr_true)
353 is_activate = true;
354 }
355
356 Trace::eDebugLevel dbg_lvl = def_config.debugLevel();
357 {
358 if (dbg_lvl_str==ustr_none)
359 dbg_lvl = Trace::None;
360 if (dbg_lvl_str==ustr_lowest)
361 dbg_lvl = Trace::Lowest;
362 if (dbg_lvl_str==ustr_low)
363 dbg_lvl = Trace::Low;
364 if (dbg_lvl_str==ustr_medium)
365 dbg_lvl = Trace::Medium;
366 if (dbg_lvl_str==ustr_high)
367 dbg_lvl = Trace::High;
368 if (dbg_lvl_str==ustr_highest)
369 dbg_lvl = Trace::Highest;
370 }
371
372 bool is_print_class_name = true;
373 builtInGetValue(is_print_class_name,print_class_name_str);
374 bool is_print_elapsed_time = false;
375 builtInGetValue(is_print_elapsed_time,print_elapsed_time_str);
376 int flags = Trace::PF_Default;
377 if (!is_print_class_name)
378 flags |= Trace::PF_NoClassName;
379 if (is_print_elapsed_time)
380 flags |= Trace::PF_ElapsedTime;
381
382 TraceClassConfig mc (is_activate,is_parallel_activate,dbg_lvl,flags);
383 if (do_log)
384 trace->log() << "Config " << mc.isActivated() << ' '
385 << mc.isParallelActivated() << ' ' << module_name;
386 trace->setClassConfig(module_name,mc);
387 if (do_log)
388 trace->log() << "Config module class"
389 << " name=" << module_name
390 << " activated=" << is_activate
391 << " dbglvl=" << (int)dbg_lvl;
392 }
393}
394
395/*---------------------------------------------------------------------------*/
396/*---------------------------------------------------------------------------*/
397
398} // End namespace Arcane
399
400/*---------------------------------------------------------------------------*/
401/*---------------------------------------------------------------------------*/
Interface de l'application.
virtual ITraceMng * traceMng() const =0
Gestionnaire de traces.
Interface du gestionnaire de configuration d'un gestionnnaire de trace.
static IXmlDocumentHolder * createNull()
Créé et retourne un document nul.
static IXmlDocumentHolder * loadFromBuffer(Span< const Byte > buffer, const String &name, ITraceMng *tm)
Charge un document XML.
Definition DomUtils.cc:426
Lecteur des fichiers de maillage via la bibliothèque LIMA.
Definition Lima.cc:120
Gestion du comportement des traces.
void setStandardOutputVerbosityLevel(Int32 level) override
Niveau de verbosité sur le flot de sortie standard (stdout).
void setIsParallelOutput(bool v) override
Indique si en parallèle tous les rangs sortent les traces dans un fichier.
void setClassConfigFromXmlBuffer(ITraceMng *trace, ByteConstArrayView bytes) override
Positionne les valeurs des TraceClassConfig de trace via les données contenues dans bytes.
void setIsDebug(bool v) override
Indique si les sorties de débug sont actives.
void setIsParallel(bool v) override
Indique si le parallélisme est actif.
void setIsMasterHasOutputFile(bool active) override
Indique si un ITraceMng maître sort les traces dans un fichier en plus de la sortie standard.
void initializeTraceMng(ITraceMng *trace, Int32 rank) override
Initialise trace.
void setDefaultVerboseLevel(ITraceMng *trace, Int32 minimal_level) override
void setVerbosityLevel(Int32 level) override
Niveau de verbosité.
void build() override
Construit l'instance.
Vue constante d'un tableau de type T.
Interface du gestionnaire de traces.
virtual void setMaster(bool is_master)=0
Positionne l'état 'maitre' de l'instance.
virtual bool setInfoActivated(bool v)=0
Modifie l'état d'activation des messages d'info.
virtual void setTraceId(const String &id)=0
Positionne l'identifiant du gestionnnaire.
virtual ARCCORE_DEPRECATED_2018 void setRedirectStream(std::ostream *o)=0
Redirige tous les messages sur le flot o.
virtual void setStandardOutputVerbosityLevel(Int32 level)=0
Positionne le niveau de verbosité des sorties sur std::cout.
virtual void setVerbosityLevel(Int32 level)=0
Positionne le niveau de verbosité des sorties.
virtual void finishInitialize()=0
Termine l'initialisation.
Constructeur de chaîne de caractère unicode.
Chaîne de caractères unicode.
bool null() const
Retourne true si la chaîne est nulle.
Definition String.cc:304
-*- tab-width: 2; indent-tabs-mode: nil; coding: utf-8-with-signature -*-
Span< const std::byte > ByteConstSpan
Vue en lecture seule d'un tableau à une dimension de caractères.
Definition UtilsTypes.h:706
ConstArrayView< Byte > ByteConstArrayView
Equivalent C d'un tableau à une dimension de caractères.
Definition UtilsTypes.h:634
@ PF_ElapsedTime
Affichage du temps écoulé
@ PF_NoClassName
Affichage ou non de la classe de message.
eDebugLevel
Niveau de debug des traces.
@ Lowest
Pas de d'informations de débug.