// @(#)root/base:$Name: $:$Id: TMessageHandler.cxx,v 1.5 2005/06/23 06:24:27 brun Exp $
// Author: Rene Brun 11/11/99
/*************************************************************************
* Copyright (C) 1995-2000, Rene Brun and Fons Rademakers. *
* All rights reserved. *
* *
* For the licensing terms see $ROOTSYS/LICENSE. *
* For the list of contributors see $ROOTSYS/README/CREDITS. *
*************************************************************************/
//////////////////////////////////////////////////////////////////////////
// //
// TMessageHandler //
// //
// Handle messages that might be generated by the system. //
// By default a handler only keeps track of the different messages //
// generated for a specific class. By deriving from this class and //
// overriding Notify() one can implement custom message handling. //
// In Notify() one has access to the message id and the object //
// generating the message. One can install more than one message //
// handler per class. A message handler can be removed or again //
// added when needed. //
// All Root "Warnings" are logged as message 1001 //
// All Root "Errors" are logged as message 1002 //
// All Root "SysErrors" are logged as message 1003 //
// All Root "Fatals" are logged as message 1004 //
// //
//////////////////////////////////////////////////////////////////////////
#include "TMessageHandler.h"
#include "TClass.h"
#include "TROOT.h"
#include "TVirtualMutex.h"
ClassImp(TMessageHandler)
//______________________________________________________________________________
TMessageHandler::TMessageHandler(const TClass *cl, Bool_t derived)
{
// Create a new message handler for class cl and add it to the list
// of message handlers.
fClass = cl;
fMessObj = 0;
fMessId = 0;
fSize = 0;
fCnts = 0;
fMessIds = 0;
fDerived = derived;
if (fClass) SetName(fClass->GetName());
else SetName("DefaultMessageHandler");
Add();
}
//______________________________________________________________________________
TMessageHandler::TMessageHandler(const char *cl, Bool_t derived)
{
// Create a new message handler for class named cl and add it to the list
// of message handlers.
fClass = gROOT->GetClass(cl);
fMessObj = 0;
fMessId = 0;
fSize = 0;
fCnts = 0;
fMessIds = 0;
fDerived = derived;
SetName(cl);
SetName(fClass->GetName());
Add();
}
//______________________________________________________________________________
TMessageHandler:: ~TMessageHandler()
{
// Clean up the messagehandler.
Remove();
if (fSize <= 0) return;
delete [] fCnts;
delete fMessIds;
}
//______________________________________________________________________________
void TMessageHandler::Add()
{
// Add this message handler to the list of messages handlers.
R__LOCKGUARD2(gROOTMutex);
gROOT->GetListOfMessageHandlers()->Add(this);
}
//______________________________________________________________________________
Int_t TMessageHandler::GetMessageCount(Int_t messId) const
{
// Return counter for message with ID=messid.
if (fSize <= 0) return 0;
for (Int_t i=0;i<fSize;i++) {
if (fMessIds[i] == messId) return fCnts[i];
}
return 0;
}
//______________________________________________________________________________
Int_t TMessageHandler::GetTotalMessageCount() const
{
// Return total number of messages.
if (fSize <= 0) return 0;
Int_t count = 0;
for (Int_t i=0;i<fSize;i++) {
count += fCnts[i];
}
return count;
}
//______________________________________________________________________________
void TMessageHandler::HandleMessage(Int_t id, const TObject *obj)
{
// Store message origin, keep statistics and call Notify().
// check if message must be managed by this message handler
if (fClass) {
if (fDerived) {
if(!obj->InheritsFrom(fClass)) return;
} else {
if (obj->IsA() != fClass) return;
}
}
fMessId = id;
fMessObj = obj;
Notify();
// increment statistics
Int_t i;
// first message
if (fSize <=0) {
fSize = 1;
fCnts = new Int_t[fSize];
fMessIds = new Int_t[fSize];
} else {
// already existing message
for (i=0;i<fSize;i++) {
if (fMessIds[i] == fMessId) {
fCnts[i]++;
return;
}
}
// new message
fSize++;
Int_t *newCnts = new Int_t[fSize];
Int_t *newMessIds = new Int_t[fSize];
for (i=0;i<fSize-1;i++) {
newCnts[i] = fCnts[i];
newMessIds[i] = fMessIds[i];
}
delete [] fCnts;
delete [] fMessIds;
fCnts = newCnts;
fMessIds = newMessIds;
}
fCnts[fSize-1] = 1;
fMessIds[fSize-1] = fMessId;
}
//______________________________________________________________________________
Bool_t TMessageHandler::Notify()
{
// This method must be overridden to handle object notifcation.
if (fClass) return kFALSE;
// case of default handler
// encode class number in message id
if (!fMessObj) return kFALSE;
Int_t uid = Int_t(fMessObj->IsA()->GetUniqueID());
fMessId += 10000*uid;
fMessId = -fMessId;
return kFALSE;
}
//______________________________________________________________________________
void TMessageHandler::Print(Option_t *) const
{
// Print statistics for this message handler.
printf("\n ****** Message Handler: %s has a total of %d messages\n",GetName(),GetTotalMessageCount());
if (fSize <= 0) return;
Int_t id, uid;
const TClass *cl;
TIter next(gROOT->GetListOfClasses());
for (Int_t i=0;i<fSize;i++) {
id = fMessIds[i];
cl = fClass;
if (id < 0) {
id = -id;
uid = id/10000;
id = id%10000;
next.Reset();
while ((cl=(TClass*)next())) {
if (cl->GetUniqueID() == UInt_t(uid)) break;
}
}
if (!cl) cl = gROOT->IsA();
if (id == 1001) {
printf(" Class: %-20s WARNINGs has %d counts\n",cl->GetName(),fCnts[i]);
continue;
}
if (id == 1002) {
printf(" Class: %-20s ERRORs has %d counts\n",cl->GetName(),fCnts[i]);
continue;
}
printf(" Class: %-20s MessID = %5d has %d counts\n",cl->GetName(),id,fCnts[i]);
}
}
//______________________________________________________________________________
void TMessageHandler::Remove()
{
// Remove this message handler from the list of messages handlers.
R__LOCKGUARD2(gROOTMutex);
gROOT->GetListOfMessageHandlers()->Remove(this);
}
ROOT page - Class index - Class Hierarchy - Top of the page
This page has been automatically generated. If you have any comments or suggestions about the page layout send a mail to ROOT support, or contact the developers with any questions or problems regarding ROOT.