[0d0e60]: libpp / callgraph_container.h Maximize Restore History

Download this file

callgraph_container.h    102 lines (83 with data), 2.9 kB

  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
/**
* @file callgraph_container.h
* Container associating symbols and caller/caller symbols
*
* @remark Copyright 2004 OProfile authors
* @remark Read the file COPYING
*
* @author Philippe Elie
* @author John Levon
*/
#ifndef CALLGRAPH_CONTAINER_H
#define CALLGRAPH_CONTAINER_H
#include <set>
#include <list>
#include <string>
#include "bfd.h"
#include "profile_container.h"
#include "symbol.h"
#include "symbol_functors.h"
class inverted_profile;
/**
* Yes this look like weird since we store a callee_counts w/o knowning the
* callee. It's designed in this way because it allows symetric map in
* callee_caller_recorder, cg_symbol can be get only through public interface
* of callee_caller_recorder which hide potential misuse of this struct.
*/
struct cg_symbol : public symbol_entry {
cg_symbol(symbol_entry const & symb) : symbol_entry(symb) {}
cg_symbol() {}
count_array_t self_counts;
count_array_t callee_counts;
};
/// During building a callgraph_container we store all caller/callee
/// relationship in this container.
class caller_callee_recorder {
public:
~caller_callee_recorder();
void add_arc(cg_symbol const & caller, cg_symbol const * callee);
/// Finalize the recording after all arc has been added to propagate
/// callee counts.
void fixup_callee_counts();
// sorted sequence of cg_symbol.
vector<cg_symbol> get_arc() const;
vector<cg_symbol> get_callee(cg_symbol const &) const;
vector<cg_symbol> get_caller(cg_symbol const &) const;
private:
cg_symbol const * find_caller(cg_symbol const &) const;
typedef multimap<cg_symbol, cg_symbol const *, less_symbol> map_t;
typedef map_t::const_iterator iterator;
map_t caller_callee;
map_t callee_caller;
};
class callgraph_container {
public:
/**
* populate the container, must be called one time only.
* @param iprofiles sample file list including callgraph files.
*
* Currently all error core dump.
*/
void populate(std::list<inverted_profile> const & iprofiles);
/// These just dispatch to callee_caller_recorder. It's the way client
/// code acquire results.
vector<cg_symbol> get_arc() const;
vector<cg_symbol> get_callee(cg_symbol const &) const;
vector<cg_symbol> get_caller(cg_symbol const &) const;
private:
/** Record caller/callee for one cg file
* @param profile one callgraph file stored in a profile_t
* @param bfd_caller the caller bfd
* @param bfd_callee the callee bfd
* @param app_name the owning application
* @param symbols the profile_container holding all non cg samples.
*/
void add(profile_t const & profile, op_bfd const & bfd_caller,
op_bfd const & bfd_callee, string const & app_name,
profile_container const & symbols);
/// add fake arc <from, NULL> to record leaf symbols.
void add_leaf_arc(profile_container const & symbols);
/// A structured representation of the callgraph.
caller_callee_recorder recorder;
};
#endif /* !CALLGRAPH_CONTAINER_H */