format_output.h revision cc2ee177dbb3befca43e36cfc56778b006c3d050
1/**
2 * @file format_output.h
3 * outputting format for symbol lists
4 *
5 * @remark Copyright 2002 OProfile authors
6 * @remark Read the file COPYING
7 *
8 * @author Philippe Elie
9 * @author John Levon
10 */
11
12#ifndef FORMAT_OUTPUT_H
13#define FORMAT_OUTPUT_H
14
15#include "config.h"
16
17#include <string>
18#include <map>
19#include <iosfwd>
20
21#include "format_flags.h"
22#include "symbol.h"
23
24class symbol_entry;
25class sample_entry;
26class callgraph_container;
27class profile_container;
28class diff_container;
29
30namespace format_output {
31
32/// base class for formatter, handle common options to formatter
33class formatter {
34public:
35	formatter();
36	virtual ~formatter();
37
38	/// add a given column
39	void add_format(format_flags flag);
40
41	/// set the need_header boolean to false
42	void show_header(bool);
43	/// format for 64 bit wide VMAs
44	void vma_format_64bit(bool);
45	/// show long (full path) filenames
46	void show_long_filenames(bool);
47	/// use global count rather symbol count for details percent
48	void show_global_percent(bool);
49
50	/**
51	 * Set the number of collected profile classes. Each class
52	 * will output sample count and percentage in extra columns.
53	 *
54	 * This class assumes that the profile information has been
55	 * populated with the right number of classes.
56	 */
57	void set_nr_classes(size_t nr_classes);
58
59	/// output table header, implemented by calling the virtual function
60	/// output_header_field()
61	void output_header(std::ostream & out);
62
63protected:
64	struct counts_t {
65		/// total sample count
66		count_array_t total;
67		/// samples so far
68		count_array_t cumulated_samples;
69		/// percentage so far
70		count_array_t cumulated_percent;
71		/// detailed percentage so far
72		count_array_t cumulated_percent_details;
73	};
74
75	/// data passed for output
76	struct field_datum {
77		field_datum(symbol_entry const & sym,
78		            sample_entry const & s,
79			    size_t pc, counts_t & c, double d = 0.0)
80			: symbol(sym), sample(s), pclass(pc),
81			  counts(c), diff(d) {}
82		symbol_entry const & symbol;
83		sample_entry const & sample;
84		size_t pclass;
85		mutable counts_t & counts;
86		double diff;
87	};
88
89	/// format callback type
90	typedef std::string (formatter::*fct_format)(field_datum const &);
91
92	/** @name format functions.
93	 * The set of formatting functions, used internally by output().
94	 */
95	//@{
96	std::string format_vma(field_datum const &);
97	std::string format_symb_name(field_datum const &);
98	std::string format_image_name(field_datum const &);
99	std::string format_app_name(field_datum const &);
100	std::string format_linenr_info(field_datum const &);
101	std::string format_nr_samples(field_datum const &);
102	std::string format_nr_cumulated_samples(field_datum const &);
103	std::string format_percent(field_datum const &);
104	std::string format_cumulated_percent(field_datum const &);
105	std::string format_percent_details(field_datum const &);
106	std::string format_cumulated_percent_details(field_datum const &);
107	std::string format_diff(field_datum const &);
108	//@}
109
110	/// decribe one field of the colummned output.
111	struct field_description {
112		field_description() {}
113		field_description(std::size_t w, std::string h, fct_format f)
114			: width(w), header_name(h), formatter(f) {}
115
116		std::size_t width;
117		std::string header_name;
118		fct_format formatter;
119	};
120
121	typedef std::map<format_flags, field_description> format_map_t;
122
123	/// actually do output
124	void do_output(std::ostream & out, symbol_entry const & symbol,
125		      sample_entry const & sample, counts_t & c,
126	              diff_array_t const & = diff_array_t(),
127	              bool hide_immutable_field = false);
128
129	/// returns the nr of char needed to pad this field
130	size_t output_header_field(std::ostream & out, format_flags fl,
131	                           size_t padding);
132
133	/// returns the nr of char needed to pad this field
134	size_t output_field(std::ostream & out, field_datum const & datum,
135			   format_flags fl, size_t padding,
136			   bool hide_immutable);
137
138	/// stores functors for doing actual formatting
139	format_map_t format_map;
140
141	/// number of profile classes
142	size_t nr_classes;
143
144	/// total counts
145	counts_t counts;
146
147	/// formatting flags set
148	format_flags flags;
149	/// true if we need to format as 64 bits quantities
150	bool vma_64;
151	/// false if we use basename(filename) in output rather filename
152	bool long_filenames;
153	/// true if we need to show header before the first output
154	bool need_header;
155	/// bool if details percentage are relative to total count rather to
156	/// symbol count
157	bool global_percent;
158};
159
160
161/// class to output in a columned format symbols and associated samples
162class opreport_formatter : public formatter {
163public:
164	/// build a ready to use formatter
165	opreport_formatter(profile_container const & profile);
166
167	/** output a vector of symbols to out according to the output format
168	 * specifier previously set by call(s) to add_format() */
169	void output(std::ostream & out, symbol_collection const & syms);
170
171	/// set the output_details boolean
172	void show_details(bool);
173
174private:
175
176	/** output one symbol symb to out according to the output format
177	 * specifier previously set by call(s) to add_format() */
178	void output(std::ostream & out, symbol_entry const * symb);
179
180	/// output details for the symbol
181	void output_details(std::ostream & out, symbol_entry const * symb);
182
183	/// container we work from
184	profile_container const & profile;
185
186	/// true if we need to show details for each symbols
187	bool need_details;
188};
189
190
191/// class to output in a columned format caller/callee and associated samples
192class cg_formatter : public formatter {
193public:
194	/// build a ready to use formatter
195	cg_formatter(callgraph_container const & profile);
196
197	/** output callgraph information according to the previously format
198	 * specifier set by call(s) to add_format() */
199	void output(std::ostream & out, cg_collection const & syms);
200};
201
202/// class to output a columned format symbols plus diff values
203class diff_formatter : public formatter {
204public:
205	/// build a ready to use formatter
206	diff_formatter(diff_container const & profile);
207
208	/**
209	 * Output a vector of symbols to out according to the output
210	 * format specifier previously set by call(s) to add_format()
211	 */
212	void output(std::ostream & out, diff_collection const & syms);
213
214private:
215	/// output a single symbol
216	void output(std::ostream & out, diff_symbol const & sym);
217
218};
219
220} // namespace format_output
221
222#endif /* !FORMAT_OUTPUT_H */
223