⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 vglog.cpp

📁 Linux平台下的内核及程序调试器
💻 CPP
📖 第 1 页 / 共 3 页
字号:
/* --------------------------------------------------------------------- * Implementation of VgLog                                     vglog.cpp * VgLog: QDomDocument based representation of a valgrind xml log. * --------------------------------------------------------------------- * This file is part of Valkyrie, a front-end for Valgrind * Copyright (c) 2000-2006, OpenWorks LLP <info@open-works.co.uk> * This program is released under the terms of the GNU GPL v.2 * See the file LICENSE.GPL for the full license details. */#include "vglog.h"#include <qtextstream.h>#include <assert.h>/* different implementations for valkyrie/vk_logmerge */extern void vklmPrint( int verb, const char* msg, ... )   __attribute__((format (printf, 2, 3)));extern void vklmPrintErr( const char* msg, ... )   __attribute__((format (printf, 1, 2)));/**********************************************************************//*  setup static class maps  - avoids setting up map in class cons, but keeps map where it belongs*/VgElement::ElemTypeMap setupElemTypeMap() {   VgElement::ElemTypeMap etmap;   etmap["valgrindoutput"]   = VgElement::ROOT;   etmap["protocolversion"]  = VgElement::PROTOCOL;   etmap["preamble"]         = VgElement::PREAMBLE;   etmap["pid"]              = VgElement::PID;   etmap["ppid"]             = VgElement::PPID;   etmap["tool"]             = VgElement::TOOL;   etmap["logfilequalifier"] = VgElement::LOGQUAL;   etmap["var"]              = VgElement::VAR;   etmap["value"]            = VgElement::VALUE;   etmap["usercomment"]      = VgElement::COMMENT;   etmap["args"]             = VgElement::ARGS;   etmap["vargv"]            = VgElement::VARGV;   etmap["argv"]             = VgElement::ARGV;   etmap["exe"]              = VgElement::EXE;   etmap["arg"]              = VgElement::ARG;   etmap["status"]           = VgElement::STATUS;   etmap["state"]            = VgElement::STATE;   etmap["time"]             = VgElement::TIME;   etmap["error"]            = VgElement::ERROR;   etmap["unique"]           = VgElement::UNIQUE;   etmap["tid"]              = VgElement::TID;   etmap["kind"]             = VgElement::KIND;   etmap["what"]             = VgElement::WHAT;   etmap["stack"]            = VgElement::STACK;   etmap["frame"]            = VgElement::FRAME;   etmap["ip"]               = VgElement::IP;   etmap["obj"]              = VgElement::OBJ;   etmap["fn"]               = VgElement::FN;   etmap["dir"]              = VgElement::SRCDIR;   etmap["file"]             = VgElement::SRCFILE;   etmap["line"]             = VgElement::LINE;   etmap["auxwhat"]          = VgElement::AUXWHAT;   etmap["errorcounts"]      = VgElement::ERRORCOUNTS;   etmap["pair"]             = VgElement::PAIR;   etmap["count"]            = VgElement::COUNT;   etmap["suppcounts"]       = VgElement::SUPPCOUNTS;   etmap["name"]             = VgElement::NAME;   etmap["leakedbytes"]      = VgElement::LEAKEDBYTES;   etmap["leakedblocks"]     = VgElement::LEAKEDBLOCKS;   return etmap;}VgElement::ElemTypeMap VgElement::elemtypeMap = setupElemTypeMap();VgError::LeakKindMap setupLeakKindMap() {   VgError::LeakKindMap lkmap;   lkmap["Leak_DefinitelyLost"] = VgError::UNREACHED;   lkmap["Leak_IndirectlyLost"] = VgError::INDIRECT;   lkmap["Leak_PossiblyLost"]   = VgError::INTERIOR;   lkmap["Leak_StillReachable"] = VgError::PROPER;   return lkmap;}VgError::LeakKindMap VgError::leakKindMap = setupLeakKindMap();/**********************************************************************//*  Search direct children for first/last element of 'tagname'*/VgElement VgElement::getFirstElem( QString tagname ) const{   //  vklmPrintErr("getFirstElem(): %s", tagname.latin1());   QDomElement e;   for ( e = firstChild().toElement(); !e.isNull();         e = e.nextSibling().toElement() ) {      //    vklmPrintErr(" - %s",e.tagName().latin1());      if (e.tagName() == tagname)         return (VgElement&)e;   }   return VgElement();}VgElement VgElement::getLastElem( QString tagname ) const{   QDomElement e;   for ( e = lastChild().toElement(); !e.isNull();         e = e.previousSibling().toElement() ) {      if (e.tagName() == tagname)         return (VgElement&)e;   }   return VgElement();}VgElement::ElemType VgElement::elemType(){   ElemTypeMap::Iterator it = elemtypeMap.find( tagName() );   if ( it == elemtypeMap.end() )      return VgElement::NUM_ELEMS;   return it.data(); }/*  Convert leaf element content to integer.  Returns 0 if conversion fails*/unsigned long VgElement::toULong( bool* ok ){   if (!isLeaf()) {      *ok = false;      return 0;   }   QDomText textNode = firstChild().toText();   if (textNode.isNull()) {      *ok = false;      return 0;   }   QString numStr = textNode.data();   unsigned long num = numStr.toULong(ok);   if (!ok) {      *ok = false;      return 0;   }   return num;}/*  Sets content for a leaf element*/bool VgElement::setContent( QString content ){   if (!isLeaf()) return false;   QDomText textNode = firstChild().toText();   if (textNode.isNull())      return false;   textNode.setData( content );   return true;}/*  Gets content for a leaf element*/QString VgElement::getContent(){   if (!isLeaf()) return "";   QDomText textNode = firstChild().toText();   if (textNode.isNull())      return "";   return textNode.data();}/*  add slave elem count to this count*/bool VgElement::updateCount( VgElement sElemNum ){   if (!isLeaf()) return false;   bool ok;   unsigned long mNum = toULong( &ok );   if (!ok) return false;   unsigned long sNum = sElemNum.toULong( &ok );   if (!ok) return false;   if (!setContent( QString::number( mNum + sNum ) ) )      return false;   return true;}bool VgElement::isLeaf(){   return ( (childNodes().count() == 1) &&            (firstChild().childNodes().count() == 0) );}/**********************************************************************/QString VgPreamble::toPlainTxt(){   QString output_str;   for ( QDomNode n=firstChild(); !n.isNull(); n=n.nextSibling() ) {      output_str += n.toElement().text() + "\n";       }   return output_str;}/**********************************************************************//* "", "RUNNING", "FINISHED" */VgStatus::StateType VgStatus::state(){   QDomElement n_state = firstChild().toElement();   if (n_state.isNull())      return INIT;   if (n_state.text() == "RUNNING")      return RUNNING;   return FINISHED;}/**********************************************************************/bool VgFrame::operator==( const VgFrame& frame2 ) const{   QDomNodeList frame_details1 = childNodes();   assert( frame_details1.count() >= 1 );  /* only ip guaranteed */   QDomElement iptr1 = frame_details1.item( 0 ).toElement();   QDomElement objt1 = frame_details1.item( 1 ).toElement();   QDomElement func1 = frame_details1.item( 2 ).toElement();   QDomElement diry1 = frame_details1.item( 3 ).toElement();   QDomElement file1 = frame_details1.item( 4 ).toElement();   QDomElement line1 = frame_details1.item( 5 ).toElement();   QDomNodeList frame_details2 = frame2.childNodes();   assert( frame_details2.count() >= 1 );  /* only ip guaranteed */   QDomElement iptr2 = frame_details2.item( 0 ).toElement();   QDomElement objt2 = frame_details2.item( 1 ).toElement();   QDomElement func2 = frame_details2.item( 2 ).toElement();   QDomElement diry2 = frame_details2.item( 3 ).toElement();   QDomElement file2 = frame_details2.item( 4 ).toElement();   QDomElement line2 = frame_details2.item( 5 ).toElement();   /* a frame may be the 'same' as another even if it is      missing some data - do the best comparison we can */     /* only field guaranteed to be present is 'ip'.      comparing 'ip' is dodgy, so we try our hardest not to. */     /* A: test fields: 'dir', 'file', 'line' */   if ( !diry1.isNull() && !diry2.isNull() &&        !file1.isNull() && !file2.isNull() &&        !line1.isNull() && !line2.isNull() ) {      vklmPrint( 3, "frame test A: dir, file, line" );      if (diry1.text() != diry2.text() ||          file1.text() != file2.text() ||          line1.text() != line2.text())         return false;      return true;   }     /* B: test fields: 'file', 'line' */   if ( !file1.isNull() && !file2.isNull() &&        !line1.isNull() && !line2.isNull() ) {      vklmPrint( 3, "frame test B: file, line" );      if (file1.text() != file2.text() ||          line1.text() != line2.text())         return false;      return true;   }     /* C: test fields: 'fn', 'ip' */   if ( !func1.isNull() && !func2.isNull() ) {      vklmPrint( 3, "frame test C: func, ip" );      if (func1.text() != func2.text() ||          iptr1.text() != iptr2.text())         return false;      return true;   }     /* D: test field: 'ip' */   vklmPrint( 3, "frame test D: ip only" );   if (iptr1.text() != iptr2.text())      return false;   return true;}bool VgFrame::operator!=( const VgFrame& frame2 ) const{   return !operator==(frame2);}/* ref: coregrind/m_debuginfo/symtab.c :: VG_(describe_IP) *//* CAB: why don't print dirname for non-xml ? */QString VgFrame::describe_IP( bool withPath/*=false*/ ){   QDomNodeList frame_details = childNodes();   assert( frame_details.count() >= 1 );  /* only ip guaranteed */   QDomElement ip     = frame_details.item( 0 ).toElement();   QDomElement obj    = frame_details.item( 1 ).toElement();   QDomElement fn     = frame_details.item( 2 ).toElement();   QDomElement dir    = frame_details.item( 3 ).toElement();   QDomElement srcloc = frame_details.item( 4 ).toElement();   QDomElement line   = frame_details.item( 5 ).toElement();   bool  know_fnname  = !fn.isNull();   bool  know_objname = !obj.isNull();   bool  know_srcloc  = !srcloc.isNull() && !line.isNull();   bool  know_dirinfo = !dir.isNull();   QString str = ip.text() + ": ";   if (know_fnname) {      str += fn.text();      if (!know_srcloc && know_objname)         str += " (in " + obj.text() + ")";   } else if (know_objname && !know_srcloc) {      str += "(within " + obj.text() + ")";   } else {      str += "???";   }   if (know_srcloc) {      QString path;      if ( withPath && know_dirinfo )         path = dir.text() + "/";      path += srcloc.text();      str += " (" + path + ":" + line.text() + ")";   }   return str;}/**********************************************************************/bool VgError::isLeak(){   QString kind = getFirstElem( "kind" ).text();   return kind.startsWith( "Leak_" );}QString VgError::toPlainTxt(){   if (firstChild().isNull())      return "";   QString output_str;   QDomNode n = firstChild();   for ( QDomNode n=firstChild(); !n.isNull(); n=n.nextSibling() ) {      QDomElement e = n.toElement();      if (e.tagName() == "what") {         output_str += e.text() + "\n";      }      else if (e.tagName() == "stack") {         QDomNode frame = e.firstChild();         for ( ; !frame.isNull(); frame=frame.nextSibling() ) {            QString ip_desc = ((VgFrame&)frame).describe_IP();            QString pre = (frame == e.firstChild()) ? "   at " : "   by ";            output_str += pre + ip_desc + "\n";         }      }      else if (e.tagName() == "auxwhat") {         output_str += "  " + e.text() + "\n";      }   }   output_str += "\n";   return output_str;}bool VgError::operator==( const VgError& err2 ) const{#define MAX_FRAMES_COMPARE 4   QDomElement kind1 = getFirstElem( "kind" );   QDomElement kind2 = err2.getFirstElem( "kind" );   /* test #1: is the 'kind' the same */   if (kind1.text() != kind2.text()) {      vklmPrint( 3, "=> different error kind" );      return false;   }   /* - one stack per error */   QDomElement stack1 = getFirstElem( "stack" );   QDomElement stack2 = err2.getFirstElem( "stack" );   /* - one or more frames per stack */

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -