The Gaudi Framework  master (37c0b60a)
JemallocProfileSvc.cpp
Go to the documentation of this file.
1 /***********************************************************************************\
2 * (c) Copyright 1998-2024 CERN for the benefit of the LHCb and ATLAS collaborations *
3 * *
4 * This software is distributed under the terms of the Apache version 2 licence, *
5 * copied verbatim in the file "LICENSE". *
6 * *
7 * In applying this licence, CERN does not waive the privileges and immunities *
8 * granted to it by virtue of its status as an Intergovernmental Organization *
9 * or submit itself to any jurisdiction. *
10 \***********************************************************************************/
11 // Include files
14 #include <GaudiKernel/Service.h>
15 #include <climits>
16 #include <iostream>
17 
18 // local
19 #include "JemallocProfileSvc.h"
20 
21 // including jemmalloc.h is difficult as the malloc signature is not exactly identical
22 // to the system one (issue with throw).
23 // We therefore declare mallctl here.
24 extern "C" {
25 int mallctl( const char* name, void* oldp, size_t* oldlenp, void* newp, size_t newlen );
26 }
27 
28 //-----------------------------------------------------------------------------
29 // Implementation file for class : JemallocProfileSvc
30 //
31 // 2016-01-11 : Ben Couturier
32 //-----------------------------------------------------------------------------
33 
34 //=============================================================================
35 // Initializer
36 //=============================================================================
38  StatusCode sc = base_class::initialize();
39  if ( sc.isFailure() ) return sc;
40 
41  // register to the incident service
42  static const std::string serviceName = "IncidentSvc";
43  m_incidentSvc = serviceLocator()->service( serviceName );
44  if ( !m_incidentSvc ) {
45  error() << "Cannot retrieve " << serviceName << endmsg;
46  return StatusCode::FAILURE;
47  }
48 
49  debug() << "Register to the IncidentSvc" << endmsg;
50  m_incidentSvc->addListener( this, IncidentType::BeginEvent );
51  m_incidentSvc->addListener( this, IncidentType::EndEvent );
52  for ( std::string incident : m_startFromIncidents ) { m_incidentSvc->addListener( this, incident ); }
53  for ( std::string incident : m_stopAtIncidents ) { m_incidentSvc->addListener( this, incident ); }
54 
55  // Resetting the event counter
56  m_eventNumber = 0;
57  m_profiling = false;
58 
59  // Cache whether we have start/stop incidents
61  m_hasStopIncident = ( m_stopAtIncidents.size() > 0 );
62 
63  // Checking the consistency of the start/stop events
65  info() << "Stop profiling trigger was specified but no start. Defaulting to first events" << endmsg;
67  }
68 
69  return StatusCode::SUCCESS;
70 }
71 
72 // Finalization of the service.
74  if ( m_profiling ) { stopProfiling(); }
75  // unregistering from the IncidentSvc
76  m_incidentSvc->removeListener( this, IncidentType::BeginEvent );
77  m_incidentSvc->removeListener( this, IncidentType::EndEvent );
79  return base_class::finalize();
80 }
81 
82 //=============================================================================
83 // Event handling methods
84 
85 //=============================================================================
86 
87 // Handler for incidents
88 void JemallocProfileSvc::handle( const Incident& incident ) {
89  if ( IncidentType::BeginEvent == incident.type() ) {
90  handleBegin();
91  } else if ( IncidentType::EndEvent == incident.type() ) {
92  handleEnd();
93  }
94 
95  // If already processing we can ignore the incidents for start
96  if ( !m_profiling && m_hasStartIncident ) {
97  for ( const std::string& startincident : m_startFromIncidents ) {
98  if ( startincident == incident.type() ) {
99  info() << "Starting Jemalloc profile at incident " << incident.type() << endmsg;
100  startProfiling();
101  break;
102  }
103  } // Loop on incidents
104  } // If checking incidents to start
105 
106  // If already processing we can ignore the incidents for start
107  if ( m_profiling && m_hasStopIncident ) {
108  for ( const std::string& stopincident : m_stopAtIncidents ) {
109  if ( stopincident == incident.type() ) {
110  info() << "Stopping Jemalloc profile at incident " << incident.type() << endmsg;
111  stopProfiling();
112  break;
113  }
114  } // Loop on incidents
115  } // If checking incidents to stop
116 }
117 
118 // Handler for incidents
119 // Called on at begin events
121  m_eventNumber += 1;
122 
124 }
125 
126 // Handler for incidents
127 // Called on at End events
130  ( ( m_eventNumber - m_nStartFromEvent ) % m_dumpPeriod == 0 ) ) {
131  dumpProfile();
132  }
133 
135 }
136 
137 //=============================================================================
138 // Utilities calling mallctl
139 
140 //=============================================================================
141 
146  m_profiling = true;
147  info() << "Starting Jemalloc profile at event " << m_eventNumber << endmsg;
148  mallctl( "prof.dump", NULL, NULL, NULL, 0 );
149 }
150 
155  m_profiling = false;
156  dumpProfile();
157 }
158 
163  info() << "Dumping Jemalloc profile at event " << m_eventNumber << endmsg;
164  mallctl( "prof.dump", NULL, NULL, NULL, 0 );
165 }
166 
167 //=============================================================================
168 // Declaration of the factory
JemallocProfileSvc::m_incidentSvc
SmartIF< IIncidentSvc > m_incidentSvc
Pointer to the incident service.
Definition: JemallocProfileSvc.h:71
std::string
STL class.
JemallocProfileSvc::m_hasStopIncident
bool m_hasStopIncident
Definition: JemallocProfileSvc.h:65
SmartIF::reset
void reset(TYPE *ptr=nullptr)
Set the internal pointer to the passed one disposing of the old one.
Definition: SmartIF.h:96
JemallocProfileSvc::m_nStartFromEvent
Gaudi::Property< int > m_nStartFromEvent
Definition: JemallocProfileSvc.h:51
JemallocProfileSvc
Definition: JemallocProfileSvc.h:28
mallctl
int mallctl(const char *name, void *oldp, size_t *oldlenp, void *newp, size_t newlen)
JemallocProfileSvc.h
JemallocProfileSvc::m_nStopAtEvent
Gaudi::Property< int > m_nStopAtEvent
Definition: JemallocProfileSvc.h:54
JemallocProfileSvc::handle
void handle(const Incident &incident) override
Definition: JemallocProfileSvc.cpp:88
JemallocProfileSvc::m_stopAtIncidents
Gaudi::Property< std::vector< std::string > > m_stopAtIncidents
Definition: JemallocProfileSvc.h:57
IIncidentSvc.h
StatusCode
Definition: StatusCode.h:65
endmsg
MsgStream & endmsg(MsgStream &s)
MsgStream Modifier: endmsg. Calls the output method of the MsgStream.
Definition: MsgStream.h:202
JemallocProfileSvc::startProfiling
void startProfiling()
Utility method to start profiling with jemalloc.
Definition: JemallocProfileSvc.cpp:145
JemallocProfileSvc::handleBegin
void handleBegin()
Definition: JemallocProfileSvc.cpp:120
Service.h
StatusCode::isFailure
bool isFailure() const
Definition: StatusCode.h:129
StatusCode::SUCCESS
constexpr static const auto SUCCESS
Definition: StatusCode.h:100
ConditionsStallTest.name
name
Definition: ConditionsStallTest.py:77
JemallocProfileSvc::dumpProfile
void dumpProfile()
Utility method to dump profile with jemalloc.
Definition: JemallocProfileSvc.cpp:162
JemallocProfileSvc::handleEnd
void handleEnd()
Definition: JemallocProfileSvc.cpp:128
JemallocProfileSvc::m_profiling
bool m_profiling
Status of the profiling.
Definition: JemallocProfileSvc.h:68
JemallocProfileSvc::stopProfiling
void stopProfiling()
Utility method to stop profiling with jemalloc.
Definition: JemallocProfileSvc.cpp:154
JemallocProfileSvc::m_dumpPeriod
Gaudi::Property< int > m_dumpPeriod
Definition: JemallocProfileSvc.h:59
IIncidentListener.h
DECLARE_COMPONENT
#define DECLARE_COMPONENT(type)
Definition: PluginServiceV1.h:46
JemallocProfileSvc::m_hasStartIncident
bool m_hasStartIncident
Definition: JemallocProfileSvc.h:64
JemallocProfileSvc::finalize
StatusCode finalize() override
Finalizer.
Definition: JemallocProfileSvc.cpp:73
Incident::type
const std::string & type() const
Access to the incident type.
Definition: Incident.h:48
StatusCode::FAILURE
constexpr static const auto FAILURE
Definition: StatusCode.h:101
JemallocProfileSvc::m_eventNumber
int m_eventNumber
Current event number.
Definition: JemallocProfileSvc.h:62
Incident
Definition: Incident.h:27
JemallocProfileSvc::initialize
StatusCode initialize() override
Initializer.
Definition: JemallocProfileSvc.cpp:37
Service::serviceLocator
SmartIF< ISvcLocator > & serviceLocator() const override
Retrieve pointer to service locator
Definition: Service.cpp:335
JemallocProfileSvc::m_startFromIncidents
Gaudi::Property< std::vector< std::string > > m_startFromIncidents
Definition: JemallocProfileSvc.h:52