Permalink
Browse files

PT-39529867 Added isntrumentration thread that push information to sy…

…stemtap. This is started using SIGUSR1 signal and stopped with SIGUSR2
  • Loading branch information...
1 parent 928b120 commit 584a177ff854f363fba23ef08658c4d89d558118 Joegen Baclor committed Nov 14, 2012
@@ -20,13 +20,18 @@
#include <stdint.h>
+bool system_tap_start_portlib_instrumentation(bool enableTrace);
+bool system_tap_stop_portlib_instrumentation();
+
void system_tap_queue_enqueue(const char* queue, int eventType, int queueSize);
void system_tap_queue_dequeue(const char* queue, int eventType, int queueSize);
void system_tap_timer_create(int expireTime);
void system_tap_timer_destroy();
void system_tap_timer_fire(int expireTime, int precision, int overheadUseq);
void system_tap_object_created(intptr_t pointerAddress, const char* className);
void system_tap_object_destroyed(intptr_t pointerAddress, const char* className);
+void system_tap_report_object_count(long created, long deleted);
+void system_tap_report_object_trace(intptr_t pointerAddress, const char* trace);
#endif /* INSTRUMENTATION_H_SIPXPORTLIB */
@@ -16,16 +16,92 @@
*/
#include "utl/Instrumentation.h"
+#include <execinfo.h>
+#include <string.h>
+#include <map>
+#include <set>
+#include <vector>
+#include <sstream>
+#include <boost/thread.hpp>
+
+
+#define TraceElementSize 100
+struct TraceElements
+{
+ TraceElements()
+ {
+ size = 0;
+ }
+
+ TraceElements(const TraceElements& elems)
+ {
+ for (int i = 0; i < TraceElementSize; i++)
+ {
+ trace_elems[i] = elems.trace_elems[i];
+ }
+ size = elems.size;
+ }
+
+ TraceElements& operator=(const TraceElements& elems)
+ {
+ for (int i = 0; i < TraceElementSize; i++)
+ {
+ trace_elems[i] = elems.trace_elems[i];
+ }
+ size = elems.size;
+ return *this;
+ }
+
+ void* trace_elems[TraceElementSize];
+ int size;
+};
+
+
+typedef boost::mutex mutex_critic_sec;
+typedef boost::lock_guard<mutex_critic_sec> mutex_lock;
+typedef std::map<intptr_t, TraceElements> ObjectInfo;
+typedef std::set<intptr_t> ObjectPointer;
+static bool _isIntrumentationEnabled = false;
+static bool _isBackTraceEnabled = false;
+static boost::thread* _pTapThread = 0;
+static mutex_critic_sec _objectInfoMutex;
+static ObjectInfo _objectInfo;
+static ObjectPointer _objectPointer;
+static long _createdObjectCount = 0;
+static long _deletedObjectCount = 0;
+
static const char* system_tap_queue_enqueue_queue;
static int system_tap_queue_enqueue_eventType;
static int system_tap_queue_enqueue_queueSize;
+
+
+
+
+void ubacktrace_elems(TraceElements& elems)
+{
+ elems.size = backtrace( elems.trace_elems, TraceElementSize);
+}
+
+void ubacktrace(TraceElements& elems, std::string& bt)
+{
+ char** stack_syms(backtrace_symbols(elems.trace_elems, elems.size));
+ bt.reserve(5120);
+ for (int i = 0 ; i < elems.size ; ++i )
+ bt.append(stack_syms[i]).push_back('\n');
+ free(stack_syms);
+}
+
+
void system_tap_queue_enqueue(const char* queue, int eventType, int queueSize)
{
- system_tap_queue_enqueue_queue = queue;
- system_tap_queue_enqueue_eventType = eventType;
- system_tap_queue_enqueue_queueSize = queueSize;
+ if (_isIntrumentationEnabled)
+ {
+ system_tap_queue_enqueue_queue = queue;
+ system_tap_queue_enqueue_eventType = eventType;
+ system_tap_queue_enqueue_queueSize = queueSize;
+ }
}
static const char* system_tap_queue_dequeue_queue;
@@ -34,46 +110,161 @@ static int system_tap_queue_dequeue_queueSize;
void system_tap_queue_dequeue(const char* queue, int eventType, int queueSize)
{
- system_tap_queue_dequeue_queue = queue;
- system_tap_queue_dequeue_eventType = eventType;
- system_tap_queue_dequeue_queueSize = queueSize;
+ if (_isIntrumentationEnabled)
+ {
+ system_tap_queue_dequeue_queue = queue;
+ system_tap_queue_dequeue_eventType = eventType;
+ system_tap_queue_dequeue_queueSize = queueSize;
+ }
}
static int system_tap_timer_create_expireTime;
void system_tap_timer_create(int expireTime)
{
- system_tap_timer_create_expireTime = expireTime;
+ if (_isIntrumentationEnabled)
+ {
+ system_tap_timer_create_expireTime = expireTime;
+ }
}
static int system_tap_timer_fire_precision;
static int system_tap_timer_fire_precision_overheadUseq;
static int system_tap_timer_fire_expireTime;
void system_tap_timer_fire(int expireTime, int precision, int overheadUseq)
{
- system_tap_timer_fire_expireTime = expireTime;
- system_tap_timer_fire_precision = precision;
- system_tap_timer_fire_precision_overheadUseq = overheadUseq;
+ if (_isIntrumentationEnabled)
+ {
+ system_tap_timer_fire_expireTime = expireTime;
+ system_tap_timer_fire_precision = precision;
+ system_tap_timer_fire_precision_overheadUseq = overheadUseq;
+ }
}
static int system_tap_timer_destroy_flag;
void system_tap_timer_destroy()
{
- system_tap_timer_destroy_flag = true;
+ if (_isIntrumentationEnabled)
+ {
+ system_tap_timer_destroy_flag = true;
+ }
}
-static intptr_t system_tap_object_created_pointerAddress;
-static const char* system_tap_object_created_className;
void system_tap_object_created(intptr_t pointerAddress, const char* className)
{
- system_tap_object_created_pointerAddress = pointerAddress;
- system_tap_object_created_className = className;
+ if (_isIntrumentationEnabled)
+ {
+ mutex_lock lock(_objectInfoMutex);
+ if (_isBackTraceEnabled)
+ {
+ TraceElements elem;
+ ubacktrace_elems(elem);
+ _objectInfo[pointerAddress] = elem;
+ }
+ else
+ _objectPointer.insert(pointerAddress);
+ _createdObjectCount++;
+ }
}
-static intptr_t system_tap_object_destroyed_pointerAddress;
-static const char* system_tap_object_destroyed_className;
void system_tap_object_destroyed(intptr_t pointerAddress, const char* className)
{
- system_tap_object_destroyed_pointerAddress = pointerAddress;
- system_tap_object_destroyed_className = className;
+ if (_isIntrumentationEnabled)
+ {
+ mutex_lock lock(_objectInfoMutex);
+ if (_isBackTraceEnabled)
+ _deletedObjectCount += _objectInfo.erase(pointerAddress);
+ else
+ _deletedObjectCount += _objectPointer.erase(pointerAddress);
+ }
+}
+
+static void tap_thread_sleep(unsigned long milliseconds)
+{
+ timeval sTimeout = { milliseconds / 1000, ( milliseconds % 1000 ) * 1000 };
+ select( 0, 0, 0, 0, &sTimeout );
+}
+
+static long system_tap_report_object_count_created = 0;
+static long system_tap_report_object_count_deleted = 0;
+void system_tap_report_object_count(long created, long deleted)
+{
+ system_tap_report_object_count_created = created;
+ system_tap_report_object_count_deleted = deleted;
}
+static intptr_t system_tap_report_object_trace_pointerAddress = 0;
+static const char* system_tap_report_object_trace_trace;
+void system_tap_report_object_trace(intptr_t pointerAddress, const char* trace)
+{
+ system_tap_report_object_trace_pointerAddress = pointerAddress;
+ system_tap_report_object_trace_trace = trace;
+}
+
+static void tap_thread_run_instrumentations()
+{
+ //
+ // Clear the objects from previous run
+ //
+ {
+ mutex_lock lock(_objectInfoMutex);
+ _objectInfo.clear();
+ _objectPointer.clear();
+ _createdObjectCount = 0;
+ _deletedObjectCount = 0;
+ }
+
+ _isIntrumentationEnabled = true;
+
+ while (_isIntrumentationEnabled)
+ {
+ tap_thread_sleep(100);
+ mutex_lock lock(_objectInfoMutex);
+ system_tap_report_object_count(_createdObjectCount, _deletedObjectCount);
+ }
+
+
+ {
+ mutex_lock lock(_objectInfoMutex);
+
+ if (_isBackTraceEnabled)
+ {
+ for (ObjectInfo::iterator iter = _objectInfo.begin(); iter != _objectInfo.end(); iter++)
+ {
+ std::string bt;
+ ubacktrace(iter->second, bt);
+ system_tap_report_object_trace(iter->first, bt.c_str());
+ }
+ }
+ else
+ {
+ for (ObjectPointer::const_iterator iter = _objectPointer.begin(); iter != _objectPointer.end(); iter++)
+ system_tap_report_object_trace(*iter, "TRACE DISABLED");
+ }
+
+ _objectInfo.clear();
+ _objectPointer.clear();
+ _createdObjectCount = 0;
+ _deletedObjectCount = 0;
+ }
+}
+
+bool system_tap_start_portlib_instrumentation(bool enableTrace)
+{
+ if (_pTapThread)
+ return false;
+ _isBackTraceEnabled = enableTrace;
+ _pTapThread = new boost::thread(boost::bind(tap_thread_run_instrumentations));
+ return true;
+}
+
+bool system_tap_stop_portlib_instrumentation()
+{
+ if (_pTapThread)
+ {
+ _isIntrumentationEnabled = false;
+ _pTapThread->join();
+ delete _pTapThread;
+ _pTapThread = 0;
+ }
+ return true;
+}
@@ -32,6 +32,7 @@
#include <sipXecsService/daemon.h>
#include <ForwardRules.h>
#include <SipXProxyCseObserver.h>
+#include <utl/Instrumentation.h>
#include "config.h"
//
@@ -718,20 +719,31 @@ int proxy()
}
void signal_handler(int sig) {
- switch(sig) {
+ switch(sig)
+ {
case SIGPIPE:
- Os::Logger::instance().log(FAC_SIP, PRI_INFO, "SIGPIPE caught. Ignored.");
- break;
+ Os::Logger::instance().log(FAC_SIP, PRI_INFO, "SIGPIPE caught. Ignored.");
+ break;
case SIGHUP:
- Os::Logger::instance().log(FAC_SIP, PRI_INFO, "SIGHUP caught. Ignored.");
- break;
+ Os::Logger::instance().log(FAC_SIP, PRI_INFO, "SIGHUP caught. Ignored.");
+ break;
case SIGTERM:
- gShutdownFlag = TRUE;
- Os::Logger::instance().log(FAC_SIP, PRI_INFO, "SIGTERM caught. Shutting down.");
- break;
- }
+ gShutdownFlag = TRUE;
+ Os::Logger::instance().log(FAC_SIP, PRI_INFO, "SIGTERM caught. Shutting down.");
+ break;
+
+ case SIGUSR1:
+ system_tap_start_portlib_instrumentation(true/*Bactrace enabled*/);
+ Os::Logger::instance().log(FAC_SIP, PRI_NOTICE, "SIGUSR1 caught. Starting instrumentations.");
+ break;
+
+ case SIGUSR2:
+ system_tap_stop_portlib_instrumentation();
+ Os::Logger::instance().log(FAC_SIP, PRI_NOTICE, "SIGUSR2 caught. Starting instrumentations.");
+ break;
+ }
}
// USAGE: sipXproxy [-v] [pidfile]
@@ -751,6 +763,8 @@ int main(int argc, char* argv[]) {
signal(SIGHUP, signal_handler); // catch hangup signal
signal(SIGTERM, signal_handler); // catch kill signal
signal(SIGPIPE, signal_handler); // r/w socket failure
+ signal(SIGUSR1, signal_handler);
+ signal(SIGUSR2, signal_handler);
proxy();
Os::Logger::instance().log(FAC_SIP, PRI_NOTICE, "Exiting") ;
Os::Logger::instance().flush();
Oops, something went wrong.

0 comments on commit 584a177

Please sign in to comment.