xref: /aosp_15_r20/external/blktrace/btt/output.c (revision 1a3d31e37cc95e9919fd86900a2b6a555f55952c)
1*1a3d31e3SAndroid Build Coastguard Worker /*
2*1a3d31e3SAndroid Build Coastguard Worker  * blktrace output analysis: generate a timeline & gather statistics
3*1a3d31e3SAndroid Build Coastguard Worker  *
4*1a3d31e3SAndroid Build Coastguard Worker  * Copyright (C) 2006 Alan D. Brunelle <[email protected]>
5*1a3d31e3SAndroid Build Coastguard Worker  *
6*1a3d31e3SAndroid Build Coastguard Worker  *  This program is free software; you can redistribute it and/or modify
7*1a3d31e3SAndroid Build Coastguard Worker  *  it under the terms of the GNU General Public License as published by
8*1a3d31e3SAndroid Build Coastguard Worker  *  the Free Software Foundation; either version 2 of the License, or
9*1a3d31e3SAndroid Build Coastguard Worker  *  (at your option) any later version.
10*1a3d31e3SAndroid Build Coastguard Worker  *
11*1a3d31e3SAndroid Build Coastguard Worker  *  This program is distributed in the hope that it will be useful,
12*1a3d31e3SAndroid Build Coastguard Worker  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
13*1a3d31e3SAndroid Build Coastguard Worker  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14*1a3d31e3SAndroid Build Coastguard Worker  *  GNU General Public License for more details.
15*1a3d31e3SAndroid Build Coastguard Worker  *
16*1a3d31e3SAndroid Build Coastguard Worker  *  You should have received a copy of the GNU General Public License
17*1a3d31e3SAndroid Build Coastguard Worker  *  along with this program; if not, write to the Free Software
18*1a3d31e3SAndroid Build Coastguard Worker  *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
19*1a3d31e3SAndroid Build Coastguard Worker  *
20*1a3d31e3SAndroid Build Coastguard Worker  */
21*1a3d31e3SAndroid Build Coastguard Worker #include <stdio.h>
22*1a3d31e3SAndroid Build Coastguard Worker #include "globals.h"
23*1a3d31e3SAndroid Build Coastguard Worker 
24*1a3d31e3SAndroid Build Coastguard Worker static int base_y;
25*1a3d31e3SAndroid Build Coastguard Worker 
26*1a3d31e3SAndroid Build Coastguard Worker typedef struct avg_info *ai_dip_t;
dip_q2q_dm_avg(struct d_info * dip)27*1a3d31e3SAndroid Build Coastguard Worker ai_dip_t dip_q2q_dm_avg(struct d_info *dip) { return &dip->avgs.q2q_dm; }
dip_q2a_dm_avg(struct d_info * dip)28*1a3d31e3SAndroid Build Coastguard Worker ai_dip_t dip_q2a_dm_avg(struct d_info *dip) { return &dip->avgs.q2a_dm; }
dip_q2c_dm_avg(struct d_info * dip)29*1a3d31e3SAndroid Build Coastguard Worker ai_dip_t dip_q2c_dm_avg(struct d_info *dip) { return &dip->avgs.q2c_dm; }
30*1a3d31e3SAndroid Build Coastguard Worker 
dip_q2q_avg(struct d_info * dip)31*1a3d31e3SAndroid Build Coastguard Worker ai_dip_t dip_q2q_avg(struct d_info *dip) { return &dip->avgs.q2q; }
dip_q2c_avg(struct d_info * dip)32*1a3d31e3SAndroid Build Coastguard Worker ai_dip_t dip_q2c_avg(struct d_info *dip) { return &dip->avgs.q2c; }
dip_q2a_avg(struct d_info * dip)33*1a3d31e3SAndroid Build Coastguard Worker ai_dip_t dip_q2a_avg(struct d_info *dip) { return &dip->avgs.q2a; }
dip_q2g_avg(struct d_info * dip)34*1a3d31e3SAndroid Build Coastguard Worker ai_dip_t dip_q2g_avg(struct d_info *dip) { return &dip->avgs.q2g; }
dip_s2g_avg(struct d_info * dip)35*1a3d31e3SAndroid Build Coastguard Worker ai_dip_t dip_s2g_avg(struct d_info *dip) { return &dip->avgs.s2g; }
dip_g2i_avg(struct d_info * dip)36*1a3d31e3SAndroid Build Coastguard Worker ai_dip_t dip_g2i_avg(struct d_info *dip) { return &dip->avgs.g2i; }
dip_q2m_avg(struct d_info * dip)37*1a3d31e3SAndroid Build Coastguard Worker ai_dip_t dip_q2m_avg(struct d_info *dip) { return &dip->avgs.q2m; }
dip_i2d_avg(struct d_info * dip)38*1a3d31e3SAndroid Build Coastguard Worker ai_dip_t dip_i2d_avg(struct d_info *dip) { return &dip->avgs.i2d; }
dip_d2c_avg(struct d_info * dip)39*1a3d31e3SAndroid Build Coastguard Worker ai_dip_t dip_d2c_avg(struct d_info *dip) { return &dip->avgs.d2c; }
40*1a3d31e3SAndroid Build Coastguard Worker 
41*1a3d31e3SAndroid Build Coastguard Worker typedef struct avg_info *ai_pip_t;
pip_q2q_dm_avg(struct p_info * pip)42*1a3d31e3SAndroid Build Coastguard Worker ai_pip_t pip_q2q_dm_avg(struct p_info *pip) { return &pip->avgs.q2q_dm; }
pip_q2a_dm_avg(struct p_info * pip)43*1a3d31e3SAndroid Build Coastguard Worker ai_pip_t pip_q2a_dm_avg(struct p_info *pip) { return &pip->avgs.q2a_dm; }
pip_q2c_dm_avg(struct p_info * pip)44*1a3d31e3SAndroid Build Coastguard Worker ai_pip_t pip_q2c_dm_avg(struct p_info *pip) { return &pip->avgs.q2c_dm; }
45*1a3d31e3SAndroid Build Coastguard Worker 
pip_q2q_avg(struct p_info * pip)46*1a3d31e3SAndroid Build Coastguard Worker ai_pip_t pip_q2q_avg(struct p_info *pip) { return &pip->avgs.q2q; }
pip_q2c_avg(struct p_info * pip)47*1a3d31e3SAndroid Build Coastguard Worker ai_pip_t pip_q2c_avg(struct p_info *pip) { return &pip->avgs.q2c; }
pip_q2a_avg(struct p_info * pip)48*1a3d31e3SAndroid Build Coastguard Worker ai_pip_t pip_q2a_avg(struct p_info *pip) { return &pip->avgs.q2a; }
pip_q2g_avg(struct p_info * pip)49*1a3d31e3SAndroid Build Coastguard Worker ai_pip_t pip_q2g_avg(struct p_info *pip) { return &pip->avgs.q2g; }
pip_s2g_avg(struct p_info * pip)50*1a3d31e3SAndroid Build Coastguard Worker ai_pip_t pip_s2g_avg(struct p_info *pip) { return &pip->avgs.s2g; }
pip_g2i_avg(struct p_info * pip)51*1a3d31e3SAndroid Build Coastguard Worker ai_pip_t pip_g2i_avg(struct p_info *pip) { return &pip->avgs.g2i; }
pip_q2m_avg(struct p_info * pip)52*1a3d31e3SAndroid Build Coastguard Worker ai_pip_t pip_q2m_avg(struct p_info *pip) { return &pip->avgs.q2m; }
pip_i2d_avg(struct p_info * pip)53*1a3d31e3SAndroid Build Coastguard Worker ai_pip_t pip_i2d_avg(struct p_info *pip) { return &pip->avgs.i2d; }
pip_d2c_avg(struct p_info * pip)54*1a3d31e3SAndroid Build Coastguard Worker ai_pip_t pip_d2c_avg(struct p_info *pip) { return &pip->avgs.d2c; }
55*1a3d31e3SAndroid Build Coastguard Worker 
output_section_hdr(FILE * ofp,char * hdr)56*1a3d31e3SAndroid Build Coastguard Worker void output_section_hdr(FILE *ofp, char *hdr)
57*1a3d31e3SAndroid Build Coastguard Worker {
58*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "==================== ");
59*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "%s", hdr);
60*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, " ====================\n\n");
61*1a3d31e3SAndroid Build Coastguard Worker }
62*1a3d31e3SAndroid Build Coastguard Worker 
output_hdr(FILE * ofp,char * hdr)63*1a3d31e3SAndroid Build Coastguard Worker void output_hdr(FILE *ofp, char *hdr)
64*1a3d31e3SAndroid Build Coastguard Worker {
65*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "%15s %13s %13s %13s %11s\n",
66*1a3d31e3SAndroid Build Coastguard Worker 	        hdr, "MIN", "AVG", "MAX", "N" );
67*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "--------------- ------------- ------------- ------------- -----------\n");
68*1a3d31e3SAndroid Build Coastguard Worker }
69*1a3d31e3SAndroid Build Coastguard Worker 
__output_avg(FILE * ofp,char * hdr,struct avg_info * ap,int do_easy)70*1a3d31e3SAndroid Build Coastguard Worker void __output_avg(FILE *ofp, char *hdr, struct avg_info *ap, int do_easy)
71*1a3d31e3SAndroid Build Coastguard Worker {
72*1a3d31e3SAndroid Build Coastguard Worker 	if (ap->n > 0) {
73*1a3d31e3SAndroid Build Coastguard Worker 		ap->avg = BIT_TIME(ap->total) / (double)ap->n;
74*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(ofp, "%-15s %13.9f %13.9f %13.9f %11d\n", hdr,
75*1a3d31e3SAndroid Build Coastguard Worker 			BIT_TIME(ap->min), ap->avg, BIT_TIME(ap->max), ap->n);
76*1a3d31e3SAndroid Build Coastguard Worker 
77*1a3d31e3SAndroid Build Coastguard Worker 		if (do_easy && easy_parse_avgs) {
78*1a3d31e3SAndroid Build Coastguard Worker 			fprintf(xavgs_ofp,
79*1a3d31e3SAndroid Build Coastguard Worker 				"%s %.9lf %.9lf %.9lf %d\n",
80*1a3d31e3SAndroid Build Coastguard Worker 				hdr, BIT_TIME(ap->min), ap->avg,
81*1a3d31e3SAndroid Build Coastguard Worker 						BIT_TIME(ap->max), ap->n);
82*1a3d31e3SAndroid Build Coastguard Worker 		}
83*1a3d31e3SAndroid Build Coastguard Worker 	}
84*1a3d31e3SAndroid Build Coastguard Worker }
85*1a3d31e3SAndroid Build Coastguard Worker 
avg2string(struct avg_info * ap,char * string)86*1a3d31e3SAndroid Build Coastguard Worker static inline char *avg2string(struct avg_info *ap, char *string)
87*1a3d31e3SAndroid Build Coastguard Worker {
88*1a3d31e3SAndroid Build Coastguard Worker 	if (ap->n > 0)
89*1a3d31e3SAndroid Build Coastguard Worker 		sprintf(string, "%13.9f", ap->avg);
90*1a3d31e3SAndroid Build Coastguard Worker 	else
91*1a3d31e3SAndroid Build Coastguard Worker 		sprintf(string, " ");
92*1a3d31e3SAndroid Build Coastguard Worker 	return string;
93*1a3d31e3SAndroid Build Coastguard Worker }
94*1a3d31e3SAndroid Build Coastguard Worker 
95*1a3d31e3SAndroid Build Coastguard Worker struct __oda {
96*1a3d31e3SAndroid Build Coastguard Worker 	FILE *ofp;
97*1a3d31e3SAndroid Build Coastguard Worker 	ai_dip_t (*func)(struct d_info *);
98*1a3d31e3SAndroid Build Coastguard Worker };
__output_dip_avg(struct d_info * dip,void * arg)99*1a3d31e3SAndroid Build Coastguard Worker void __output_dip_avg(struct d_info *dip, void *arg)
100*1a3d31e3SAndroid Build Coastguard Worker {
101*1a3d31e3SAndroid Build Coastguard Worker 	struct __oda *odap = arg;
102*1a3d31e3SAndroid Build Coastguard Worker 	ai_dip_t ap = odap->func(dip);
103*1a3d31e3SAndroid Build Coastguard Worker 	if (ap->n > 0) {
104*1a3d31e3SAndroid Build Coastguard Worker 		char dev_info[15];
105*1a3d31e3SAndroid Build Coastguard Worker 		ap->avg = BIT_TIME(ap->total) / (double)ap->n;
106*1a3d31e3SAndroid Build Coastguard Worker 		__output_avg(odap->ofp, make_dev_hdr(dev_info, 15, dip, 1),
107*1a3d31e3SAndroid Build Coastguard Worker 				ap, 0);
108*1a3d31e3SAndroid Build Coastguard Worker 	}
109*1a3d31e3SAndroid Build Coastguard Worker }
110*1a3d31e3SAndroid Build Coastguard Worker 
output_dip_avg(FILE * ofp,char * hdr,ai_dip_t (* func)(struct d_info *))111*1a3d31e3SAndroid Build Coastguard Worker void output_dip_avg(FILE *ofp, char *hdr, ai_dip_t (*func)(struct d_info *))
112*1a3d31e3SAndroid Build Coastguard Worker {
113*1a3d31e3SAndroid Build Coastguard Worker 	struct __oda oda = { .ofp = ofp, .func = func};
114*1a3d31e3SAndroid Build Coastguard Worker 	output_hdr(ofp, hdr);
115*1a3d31e3SAndroid Build Coastguard Worker 	dip_foreach_out(__output_dip_avg, &oda);
116*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "\n");
117*1a3d31e3SAndroid Build Coastguard Worker }
118*1a3d31e3SAndroid Build Coastguard Worker 
119*1a3d31e3SAndroid Build Coastguard Worker struct __q2d {
120*1a3d31e3SAndroid Build Coastguard Worker 	FILE *ofp;
121*1a3d31e3SAndroid Build Coastguard Worker 	void *q2d_all;
122*1a3d31e3SAndroid Build Coastguard Worker 	int n;
123*1a3d31e3SAndroid Build Coastguard Worker };
__output_q2d_histo(struct d_info * dip,void * arg)124*1a3d31e3SAndroid Build Coastguard Worker void __output_q2d_histo(struct d_info *dip, void *arg)
125*1a3d31e3SAndroid Build Coastguard Worker {
126*1a3d31e3SAndroid Build Coastguard Worker 	struct __q2d *q2dp = arg;
127*1a3d31e3SAndroid Build Coastguard Worker 
128*1a3d31e3SAndroid Build Coastguard Worker 	if (q2d_ok(dip->q2d_priv)) {
129*1a3d31e3SAndroid Build Coastguard Worker 		char dev_info[15];
130*1a3d31e3SAndroid Build Coastguard Worker 		FILE *ofp = q2dp->ofp;
131*1a3d31e3SAndroid Build Coastguard Worker 
132*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(q2dp->ofp, "%10s | ",
133*1a3d31e3SAndroid Build Coastguard Worker 					make_dev_hdr(dev_info, 15, dip, 1));
134*1a3d31e3SAndroid Build Coastguard Worker 		q2d_display(ofp, dip->q2d_priv);
135*1a3d31e3SAndroid Build Coastguard Worker 		q2d_acc(q2dp->q2d_all, dip->q2d_priv);
136*1a3d31e3SAndroid Build Coastguard Worker 		q2dp->n++;
137*1a3d31e3SAndroid Build Coastguard Worker 	}
138*1a3d31e3SAndroid Build Coastguard Worker }
139*1a3d31e3SAndroid Build Coastguard Worker 
output_q2d_histo(FILE * ofp)140*1a3d31e3SAndroid Build Coastguard Worker void output_q2d_histo(FILE *ofp)
141*1a3d31e3SAndroid Build Coastguard Worker {
142*1a3d31e3SAndroid Build Coastguard Worker 	struct __q2d __q2d = {
143*1a3d31e3SAndroid Build Coastguard Worker 		.ofp = ofp,
144*1a3d31e3SAndroid Build Coastguard Worker 		.q2d_all = q2d_alloc(),
145*1a3d31e3SAndroid Build Coastguard Worker 		.n = 0
146*1a3d31e3SAndroid Build Coastguard Worker 	};
147*1a3d31e3SAndroid Build Coastguard Worker 
148*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "%10s | ", "DEV");
149*1a3d31e3SAndroid Build Coastguard Worker 	q2d_display_header(ofp);
150*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "--------- | ");
151*1a3d31e3SAndroid Build Coastguard Worker 	q2d_display_dashes(ofp);
152*1a3d31e3SAndroid Build Coastguard Worker 	dip_foreach_out(__output_q2d_histo, &__q2d);
153*1a3d31e3SAndroid Build Coastguard Worker 
154*1a3d31e3SAndroid Build Coastguard Worker 	if (__q2d.n) {
155*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(ofp, "========== | ");
156*1a3d31e3SAndroid Build Coastguard Worker 		q2d_display_dashes(ofp);
157*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(ofp, "%10s | ", "AVG");
158*1a3d31e3SAndroid Build Coastguard Worker 		q2d_display(ofp, __q2d.q2d_all);
159*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(ofp, "\n");
160*1a3d31e3SAndroid Build Coastguard Worker 	}
161*1a3d31e3SAndroid Build Coastguard Worker 
162*1a3d31e3SAndroid Build Coastguard Worker 	q2d_free(__q2d.q2d_all);
163*1a3d31e3SAndroid Build Coastguard Worker }
164*1a3d31e3SAndroid Build Coastguard Worker 
165*1a3d31e3SAndroid Build Coastguard Worker int n_merges = 0;
166*1a3d31e3SAndroid Build Coastguard Worker struct {
167*1a3d31e3SAndroid Build Coastguard Worker 	unsigned long long nq, nd, blkmin, blkmax, total;
168*1a3d31e3SAndroid Build Coastguard Worker } merge_data;
__output_dip_merge_ratio(struct d_info * dip,void * arg)169*1a3d31e3SAndroid Build Coastguard Worker void __output_dip_merge_ratio(struct d_info *dip, void *arg)
170*1a3d31e3SAndroid Build Coastguard Worker {
171*1a3d31e3SAndroid Build Coastguard Worker 	double blks_avg;
172*1a3d31e3SAndroid Build Coastguard Worker 	char dev_info[15];
173*1a3d31e3SAndroid Build Coastguard Worker 	double ratio, q2c_n, d2c_n;
174*1a3d31e3SAndroid Build Coastguard Worker 
175*1a3d31e3SAndroid Build Coastguard Worker 	if (dip->n_qs == 0 || dip->n_ds == 0)
176*1a3d31e3SAndroid Build Coastguard Worker 		return;
177*1a3d31e3SAndroid Build Coastguard Worker 	else if (dip->n_qs < dip->n_ds)
178*1a3d31e3SAndroid Build Coastguard Worker 		dip->n_qs = dip->n_ds;
179*1a3d31e3SAndroid Build Coastguard Worker 
180*1a3d31e3SAndroid Build Coastguard Worker 	q2c_n = dip->n_qs;
181*1a3d31e3SAndroid Build Coastguard Worker 	d2c_n = dip->n_ds;
182*1a3d31e3SAndroid Build Coastguard Worker 	if (q2c_n > 0.0 && d2c_n > 0.0) {
183*1a3d31e3SAndroid Build Coastguard Worker 		if (q2c_n < d2c_n)
184*1a3d31e3SAndroid Build Coastguard Worker 			ratio = 1.0;
185*1a3d31e3SAndroid Build Coastguard Worker 		else
186*1a3d31e3SAndroid Build Coastguard Worker 			ratio = q2c_n / d2c_n;
187*1a3d31e3SAndroid Build Coastguard Worker 		blks_avg = (double)dip->avgs.blks.total / d2c_n;
188*1a3d31e3SAndroid Build Coastguard Worker 		fprintf((FILE *)arg,
189*1a3d31e3SAndroid Build Coastguard Worker 			"%10s | %8llu %8llu %7.1lf | %8llu %8llu %8llu %8llu\n",
190*1a3d31e3SAndroid Build Coastguard Worker 			make_dev_hdr(dev_info, 15, dip, 1),
191*1a3d31e3SAndroid Build Coastguard Worker 			(unsigned long long)dip->n_qs,
192*1a3d31e3SAndroid Build Coastguard Worker 			(unsigned long long)dip->n_ds,
193*1a3d31e3SAndroid Build Coastguard Worker 			ratio,
194*1a3d31e3SAndroid Build Coastguard Worker 			(unsigned long long)dip->avgs.blks.min,
195*1a3d31e3SAndroid Build Coastguard Worker 			(unsigned long long)blks_avg,
196*1a3d31e3SAndroid Build Coastguard Worker 			(unsigned long long)dip->avgs.blks.max,
197*1a3d31e3SAndroid Build Coastguard Worker 			(unsigned long long)dip->avgs.blks.total);
198*1a3d31e3SAndroid Build Coastguard Worker 
199*1a3d31e3SAndroid Build Coastguard Worker 		if (easy_parse_avgs) {
200*1a3d31e3SAndroid Build Coastguard Worker 			fprintf(xavgs_ofp,
201*1a3d31e3SAndroid Build Coastguard Worker 				"DMI %s %llu %llu %.9lf %llu %llu %llu %llu\n",
202*1a3d31e3SAndroid Build Coastguard Worker 				make_dev_hdr(dev_info, 15, dip, 0),
203*1a3d31e3SAndroid Build Coastguard Worker 				(unsigned long long)dip->n_qs,
204*1a3d31e3SAndroid Build Coastguard Worker 				(unsigned long long)dip->n_ds,
205*1a3d31e3SAndroid Build Coastguard Worker 				ratio,
206*1a3d31e3SAndroid Build Coastguard Worker 				(unsigned long long)dip->avgs.blks.min,
207*1a3d31e3SAndroid Build Coastguard Worker 				(unsigned long long)blks_avg,
208*1a3d31e3SAndroid Build Coastguard Worker 				(unsigned long long)dip->avgs.blks.max,
209*1a3d31e3SAndroid Build Coastguard Worker 				(unsigned long long)dip->avgs.blks.total);
210*1a3d31e3SAndroid Build Coastguard Worker 		}
211*1a3d31e3SAndroid Build Coastguard Worker 
212*1a3d31e3SAndroid Build Coastguard Worker 		if (n_merges++ == 0) {
213*1a3d31e3SAndroid Build Coastguard Worker 			merge_data.blkmin = dip->avgs.blks.min;
214*1a3d31e3SAndroid Build Coastguard Worker 			merge_data.blkmax = dip->avgs.blks.max;
215*1a3d31e3SAndroid Build Coastguard Worker 		}
216*1a3d31e3SAndroid Build Coastguard Worker 
217*1a3d31e3SAndroid Build Coastguard Worker 		merge_data.nq += dip->n_qs;
218*1a3d31e3SAndroid Build Coastguard Worker 		merge_data.nd += dip->n_ds;
219*1a3d31e3SAndroid Build Coastguard Worker 		merge_data.total += dip->avgs.blks.total;
220*1a3d31e3SAndroid Build Coastguard Worker 		if (dip->avgs.blks.min < merge_data.blkmin)
221*1a3d31e3SAndroid Build Coastguard Worker 			merge_data.blkmin = dip->avgs.blks.min;
222*1a3d31e3SAndroid Build Coastguard Worker 		if (dip->avgs.blks.max > merge_data.blkmax)
223*1a3d31e3SAndroid Build Coastguard Worker 			merge_data.blkmax = dip->avgs.blks.max;
224*1a3d31e3SAndroid Build Coastguard Worker 	}
225*1a3d31e3SAndroid Build Coastguard Worker }
226*1a3d31e3SAndroid Build Coastguard Worker 
output_dip_merge_ratio(FILE * ofp)227*1a3d31e3SAndroid Build Coastguard Worker void output_dip_merge_ratio(FILE *ofp)
228*1a3d31e3SAndroid Build Coastguard Worker {
229*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "%10s | %8s %8s %7s | %8s %8s %8s %8s\n", "DEV", "#Q", "#D", "Ratio", "BLKmin", "BLKavg", "BLKmax", "Total");
230*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "---------- | -------- -------- ------- | -------- -------- -------- --------\n");
231*1a3d31e3SAndroid Build Coastguard Worker 	dip_foreach_out(__output_dip_merge_ratio, ofp);
232*1a3d31e3SAndroid Build Coastguard Worker 	if (n_merges > 1) {
233*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(ofp, "---------- | -------- -------- ------- | -------- -------- -------- --------\n");
234*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(ofp, "%10s | %8s %8s %7s | %8s %8s %8s %8s\n", "DEV", "#Q", "#D", "Ratio", "BLKmin", "BLKavg", "BLKmax", "Total");
235*1a3d31e3SAndroid Build Coastguard Worker 		fprintf((FILE *)ofp,
236*1a3d31e3SAndroid Build Coastguard Worker 			"%10s | %8llu %8llu %7.1lf | %8llu %8llu %8llu %8llu\n",
237*1a3d31e3SAndroid Build Coastguard Worker 			"TOTAL", merge_data.nq, merge_data.nd,
238*1a3d31e3SAndroid Build Coastguard Worker 			(float)merge_data.nq / (float)merge_data.nd,
239*1a3d31e3SAndroid Build Coastguard Worker 			merge_data.blkmin,
240*1a3d31e3SAndroid Build Coastguard Worker 			merge_data.total / merge_data.nd,
241*1a3d31e3SAndroid Build Coastguard Worker 			merge_data.blkmax, merge_data.total);
242*1a3d31e3SAndroid Build Coastguard Worker 	}
243*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "\n");
244*1a3d31e3SAndroid Build Coastguard Worker }
245*1a3d31e3SAndroid Build Coastguard Worker 
246*1a3d31e3SAndroid Build Coastguard Worker struct __ohead_data {
247*1a3d31e3SAndroid Build Coastguard Worker 	__u64 total;
248*1a3d31e3SAndroid Build Coastguard Worker 	int n;
249*1a3d31e3SAndroid Build Coastguard Worker };
250*1a3d31e3SAndroid Build Coastguard Worker 
251*1a3d31e3SAndroid Build Coastguard Worker struct ohead_data {
252*1a3d31e3SAndroid Build Coastguard Worker 	FILE *ofp;
253*1a3d31e3SAndroid Build Coastguard Worker 	struct __ohead_data q2g, g2i, q2m, i2d, d2c, q2c;
254*1a3d31e3SAndroid Build Coastguard Worker };
255*1a3d31e3SAndroid Build Coastguard Worker 
256*1a3d31e3SAndroid Build Coastguard Worker #define __update_odp(odp, dip, fld)					\
257*1a3d31e3SAndroid Build Coastguard Worker 	do {								\
258*1a3d31e3SAndroid Build Coastguard Worker 		(odp)-> fld .total += dip->avgs. fld . total;		\
259*1a3d31e3SAndroid Build Coastguard Worker 		(odp)-> fld .n     += dip->avgs. fld . n;		\
260*1a3d31e3SAndroid Build Coastguard Worker 	} while (0)
261*1a3d31e3SAndroid Build Coastguard Worker 
__output_dip_prep_ohead(struct d_info * dip,void * arg)262*1a3d31e3SAndroid Build Coastguard Worker void __output_dip_prep_ohead(struct d_info *dip, void *arg)
263*1a3d31e3SAndroid Build Coastguard Worker {
264*1a3d31e3SAndroid Build Coastguard Worker 	if (dip->avgs.q2c.n > 0 && dip->avgs.q2c.total > 0) {
265*1a3d31e3SAndroid Build Coastguard Worker 		char dev_info[15];
266*1a3d31e3SAndroid Build Coastguard Worker 		struct ohead_data *odp = arg;
267*1a3d31e3SAndroid Build Coastguard Worker 		double q2c_total = (double)(dip->avgs.q2c.total);
268*1a3d31e3SAndroid Build Coastguard Worker 
269*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(odp->ofp,
270*1a3d31e3SAndroid Build Coastguard Worker 			"%10s | %8.4lf%% %8.4lf%% %8.4lf%% %8.4lf%% %8.4lf%%\n",
271*1a3d31e3SAndroid Build Coastguard Worker 			make_dev_hdr(dev_info, 15, dip, 1),
272*1a3d31e3SAndroid Build Coastguard Worker 			100.0 * (double)(dip->avgs.q2g.total) / q2c_total,
273*1a3d31e3SAndroid Build Coastguard Worker 			100.0 * (double)(dip->avgs.g2i.total) / q2c_total,
274*1a3d31e3SAndroid Build Coastguard Worker 			100.0 * (double)(dip->avgs.q2m.total) / q2c_total,
275*1a3d31e3SAndroid Build Coastguard Worker 			100.0 * (double)(dip->avgs.i2d.total) / q2c_total,
276*1a3d31e3SAndroid Build Coastguard Worker 			100.0 * (double)(dip->avgs.d2c.total) / q2c_total);
277*1a3d31e3SAndroid Build Coastguard Worker 
278*1a3d31e3SAndroid Build Coastguard Worker 		__update_odp(odp, dip, q2g);
279*1a3d31e3SAndroid Build Coastguard Worker 		__update_odp(odp, dip, g2i);
280*1a3d31e3SAndroid Build Coastguard Worker 		__update_odp(odp, dip, q2m);
281*1a3d31e3SAndroid Build Coastguard Worker 		__update_odp(odp, dip, i2d);
282*1a3d31e3SAndroid Build Coastguard Worker 		__update_odp(odp, dip, d2c);
283*1a3d31e3SAndroid Build Coastguard Worker 		__update_odp(odp, dip, q2c);
284*1a3d31e3SAndroid Build Coastguard Worker 	}
285*1a3d31e3SAndroid Build Coastguard Worker }
286*1a3d31e3SAndroid Build Coastguard Worker 
287*1a3d31e3SAndroid Build Coastguard Worker #define OD_AVG(od, fld, q2c)						\
288*1a3d31e3SAndroid Build Coastguard Worker 	(od. fld .n == 0) ? (double)0.0 :				\
289*1a3d31e3SAndroid Build Coastguard Worker 		(100.0 * ((double)((od). fld . total) / q2c))
290*1a3d31e3SAndroid Build Coastguard Worker 
output_dip_prep_ohead(FILE * ofp)291*1a3d31e3SAndroid Build Coastguard Worker void output_dip_prep_ohead(FILE *ofp)
292*1a3d31e3SAndroid Build Coastguard Worker {
293*1a3d31e3SAndroid Build Coastguard Worker 	double q2c;
294*1a3d31e3SAndroid Build Coastguard Worker 	struct ohead_data od;
295*1a3d31e3SAndroid Build Coastguard Worker 
296*1a3d31e3SAndroid Build Coastguard Worker 	memset(&od, 0, sizeof(od));
297*1a3d31e3SAndroid Build Coastguard Worker 	od.ofp = ofp;
298*1a3d31e3SAndroid Build Coastguard Worker 
299*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "%10s | %9s %9s %9s %9s %9s\n",
300*1a3d31e3SAndroid Build Coastguard Worker 				"DEV", "Q2G", "G2I", "Q2M", "I2D", "D2C");
301*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "---------- | --------- --------- --------- --------- ---------\n");
302*1a3d31e3SAndroid Build Coastguard Worker 	dip_foreach_out(__output_dip_prep_ohead, &od);
303*1a3d31e3SAndroid Build Coastguard Worker 
304*1a3d31e3SAndroid Build Coastguard Worker 	if (od.q2g.n == 0 && od.g2i.n == 0 && od.q2m.n == 0 &&
305*1a3d31e3SAndroid Build Coastguard Worker 						od.i2d.n == 0 && od.d2c.n == 0)
306*1a3d31e3SAndroid Build Coastguard Worker 		goto out;
307*1a3d31e3SAndroid Build Coastguard Worker 
308*1a3d31e3SAndroid Build Coastguard Worker 	q2c = od.q2c.total;
309*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "---------- | --------- --------- --------- --------- ---------\n");
310*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "%10s | %8.4lf%% %8.4lf%% %8.4lf%% %8.4lf%% %8.4lf%%\n", "Overall",
311*1a3d31e3SAndroid Build Coastguard Worker 			OD_AVG(od, q2g, q2c), OD_AVG(od, g2i, q2c),
312*1a3d31e3SAndroid Build Coastguard Worker 			OD_AVG(od, q2m, q2c), OD_AVG(od, i2d, q2c),
313*1a3d31e3SAndroid Build Coastguard Worker 			OD_AVG(od, d2c, q2c));
314*1a3d31e3SAndroid Build Coastguard Worker 
315*1a3d31e3SAndroid Build Coastguard Worker out:
316*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "\n");
317*1a3d31e3SAndroid Build Coastguard Worker }
318*1a3d31e3SAndroid Build Coastguard Worker 
319*1a3d31e3SAndroid Build Coastguard Worker struct seek_mode_info {
320*1a3d31e3SAndroid Build Coastguard Worker 	struct seek_mode_info *next;
321*1a3d31e3SAndroid Build Coastguard Worker 	long long mode;
322*1a3d31e3SAndroid Build Coastguard Worker 	int nseeks;
323*1a3d31e3SAndroid Build Coastguard Worker };
324*1a3d31e3SAndroid Build Coastguard Worker struct o_seek_info {
325*1a3d31e3SAndroid Build Coastguard Worker 	long long nseeks, median;
326*1a3d31e3SAndroid Build Coastguard Worker 	double mean;
327*1a3d31e3SAndroid Build Coastguard Worker 	struct seek_mode_info *head;
328*1a3d31e3SAndroid Build Coastguard Worker } seek_info;
329*1a3d31e3SAndroid Build Coastguard Worker int n_seeks;
330*1a3d31e3SAndroid Build Coastguard Worker 
output_seek_mode_info(FILE * ofp,struct o_seek_info * sip)331*1a3d31e3SAndroid Build Coastguard Worker void output_seek_mode_info(FILE *ofp, struct o_seek_info *sip)
332*1a3d31e3SAndroid Build Coastguard Worker {
333*1a3d31e3SAndroid Build Coastguard Worker 	struct seek_mode_info *p, *this, *new_list = NULL;
334*1a3d31e3SAndroid Build Coastguard Worker 
335*1a3d31e3SAndroid Build Coastguard Worker 	while ((this = sip->head) != NULL) {
336*1a3d31e3SAndroid Build Coastguard Worker 		sip->head = this->next;
337*1a3d31e3SAndroid Build Coastguard Worker 		this->next = NULL;
338*1a3d31e3SAndroid Build Coastguard Worker 
339*1a3d31e3SAndroid Build Coastguard Worker 		if (new_list == NULL || this->nseeks > new_list->nseeks)
340*1a3d31e3SAndroid Build Coastguard Worker 			new_list = this;
341*1a3d31e3SAndroid Build Coastguard Worker 		else if (this->nseeks == new_list->nseeks) {
342*1a3d31e3SAndroid Build Coastguard Worker 			for (p = new_list; p != NULL; p = p->next)
343*1a3d31e3SAndroid Build Coastguard Worker 				if (p->mode == this->mode)
344*1a3d31e3SAndroid Build Coastguard Worker 					break;
345*1a3d31e3SAndroid Build Coastguard Worker 
346*1a3d31e3SAndroid Build Coastguard Worker 			if (p)
347*1a3d31e3SAndroid Build Coastguard Worker 				this->nseeks += p->nseeks;
348*1a3d31e3SAndroid Build Coastguard Worker 			else
349*1a3d31e3SAndroid Build Coastguard Worker 				this->next = new_list;
350*1a3d31e3SAndroid Build Coastguard Worker 			new_list = this;
351*1a3d31e3SAndroid Build Coastguard Worker 		}
352*1a3d31e3SAndroid Build Coastguard Worker 	}
353*1a3d31e3SAndroid Build Coastguard Worker 
354*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "%10s | %15lld %15.1lf %15lld | %lld(%d)",
355*1a3d31e3SAndroid Build Coastguard Worker 	        "Average", sip->nseeks, sip->mean / sip->nseeks,
356*1a3d31e3SAndroid Build Coastguard Worker 		sip->median / sip->nseeks, new_list->mode, new_list->nseeks);
357*1a3d31e3SAndroid Build Coastguard Worker 
358*1a3d31e3SAndroid Build Coastguard Worker 	if (new_list->next) {
359*1a3d31e3SAndroid Build Coastguard Worker 		int i = 0;
360*1a3d31e3SAndroid Build Coastguard Worker 		for (p = new_list->next; p != NULL; p = p->next)
361*1a3d31e3SAndroid Build Coastguard Worker 			i++;
362*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(ofp, "\n%10s   %15s %15s %15s   ...(%d more)\n", "", "", "", "", i);
363*1a3d31e3SAndroid Build Coastguard Worker 	}
364*1a3d31e3SAndroid Build Coastguard Worker }
365*1a3d31e3SAndroid Build Coastguard Worker 
add_seek_mode_info(struct o_seek_info * sip,struct mode * mp)366*1a3d31e3SAndroid Build Coastguard Worker void add_seek_mode_info(struct o_seek_info *sip, struct mode *mp)
367*1a3d31e3SAndroid Build Coastguard Worker {
368*1a3d31e3SAndroid Build Coastguard Worker 	int i;
369*1a3d31e3SAndroid Build Coastguard Worker 	long long *lp = mp->modes;
370*1a3d31e3SAndroid Build Coastguard Worker 	struct seek_mode_info *smip;
371*1a3d31e3SAndroid Build Coastguard Worker 
372*1a3d31e3SAndroid Build Coastguard Worker 	n_seeks++;
373*1a3d31e3SAndroid Build Coastguard Worker 	for (i = 0; i < mp->nmds; i++, lp++) {
374*1a3d31e3SAndroid Build Coastguard Worker 		for (smip = sip->head; smip; smip = smip->next) {
375*1a3d31e3SAndroid Build Coastguard Worker 			if (smip->mode == *lp) {
376*1a3d31e3SAndroid Build Coastguard Worker 				smip->nseeks += mp->most_seeks;
377*1a3d31e3SAndroid Build Coastguard Worker 				break;
378*1a3d31e3SAndroid Build Coastguard Worker 			}
379*1a3d31e3SAndroid Build Coastguard Worker 		}
380*1a3d31e3SAndroid Build Coastguard Worker 		if (!smip) {
381*1a3d31e3SAndroid Build Coastguard Worker 			struct seek_mode_info *new = malloc(sizeof(*new));
382*1a3d31e3SAndroid Build Coastguard Worker 
383*1a3d31e3SAndroid Build Coastguard Worker 			new->next = sip->head;
384*1a3d31e3SAndroid Build Coastguard Worker 			sip->head = new;
385*1a3d31e3SAndroid Build Coastguard Worker 			new->mode = *lp;
386*1a3d31e3SAndroid Build Coastguard Worker 			new->nseeks = mp->most_seeks;
387*1a3d31e3SAndroid Build Coastguard Worker 
388*1a3d31e3SAndroid Build Coastguard Worker 			add_buf(new);
389*1a3d31e3SAndroid Build Coastguard Worker 		}
390*1a3d31e3SAndroid Build Coastguard Worker 	}
391*1a3d31e3SAndroid Build Coastguard Worker }
392*1a3d31e3SAndroid Build Coastguard Worker 
do_output_dip_seek_info(struct d_info * dip,FILE * ofp,int is_q2q)393*1a3d31e3SAndroid Build Coastguard Worker static void do_output_dip_seek_info(struct d_info *dip, FILE *ofp, int is_q2q)
394*1a3d31e3SAndroid Build Coastguard Worker {
395*1a3d31e3SAndroid Build Coastguard Worker 	double mean;
396*1a3d31e3SAndroid Build Coastguard Worker 	int i, nmodes;
397*1a3d31e3SAndroid Build Coastguard Worker 	long long nseeks;
398*1a3d31e3SAndroid Build Coastguard Worker 	char dev_info[15];
399*1a3d31e3SAndroid Build Coastguard Worker 	long long median;
400*1a3d31e3SAndroid Build Coastguard Worker 	struct mode m;
401*1a3d31e3SAndroid Build Coastguard Worker 	void *handle = is_q2q ? dip->q2q_handle : dip->seek_handle;
402*1a3d31e3SAndroid Build Coastguard Worker 
403*1a3d31e3SAndroid Build Coastguard Worker 	nseeks = seeki_nseeks(handle);
404*1a3d31e3SAndroid Build Coastguard Worker 	if (nseeks > 0) {
405*1a3d31e3SAndroid Build Coastguard Worker 		mean = seeki_mean(handle);
406*1a3d31e3SAndroid Build Coastguard Worker 		median = seeki_median(handle);
407*1a3d31e3SAndroid Build Coastguard Worker 		nmodes = seeki_mode(handle, &m);
408*1a3d31e3SAndroid Build Coastguard Worker 
409*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(ofp, "%10s | %15lld %15.1lf %15lld | %lld(%d)",
410*1a3d31e3SAndroid Build Coastguard Worker 			make_dev_hdr(dev_info, 15, dip, 1), nseeks, mean,
411*1a3d31e3SAndroid Build Coastguard Worker 			median, nmodes > 0 ? m.modes[0] : 0, m.most_seeks);
412*1a3d31e3SAndroid Build Coastguard Worker 		if (nmodes > 2)
413*1a3d31e3SAndroid Build Coastguard Worker 			fprintf(ofp, "\n%10s   %15s %15s %15s   ...(%d more)\n", "", "", "", "", nmodes-1);
414*1a3d31e3SAndroid Build Coastguard Worker 		else  {
415*1a3d31e3SAndroid Build Coastguard Worker 			for (i = 1; i < nmodes; i++)
416*1a3d31e3SAndroid Build Coastguard Worker 				fprintf(ofp, " %lld", m.modes[i]);
417*1a3d31e3SAndroid Build Coastguard Worker 			fprintf(ofp, "\n");
418*1a3d31e3SAndroid Build Coastguard Worker 		}
419*1a3d31e3SAndroid Build Coastguard Worker 
420*1a3d31e3SAndroid Build Coastguard Worker 		if (easy_parse_avgs) {
421*1a3d31e3SAndroid Build Coastguard Worker 			char *rec = is_q2q ? "QSK" : "DSK";
422*1a3d31e3SAndroid Build Coastguard Worker 			fprintf(xavgs_ofp,
423*1a3d31e3SAndroid Build Coastguard Worker 				"%s %s %lld %.9lf %lld %lld %d",
424*1a3d31e3SAndroid Build Coastguard Worker 				rec, make_dev_hdr(dev_info, 15, dip, 0),
425*1a3d31e3SAndroid Build Coastguard Worker 				nseeks, mean, median,
426*1a3d31e3SAndroid Build Coastguard Worker 				nmodes > 0 ? m.modes[0] : 0, m.most_seeks);
427*1a3d31e3SAndroid Build Coastguard Worker 				for (i = 1; i < nmodes; i++)
428*1a3d31e3SAndroid Build Coastguard Worker 					fprintf(xavgs_ofp, " %lld", m.modes[i]);
429*1a3d31e3SAndroid Build Coastguard Worker 				fprintf(xavgs_ofp, "\n");
430*1a3d31e3SAndroid Build Coastguard Worker 		}
431*1a3d31e3SAndroid Build Coastguard Worker 
432*1a3d31e3SAndroid Build Coastguard Worker 		seek_info.nseeks += nseeks;
433*1a3d31e3SAndroid Build Coastguard Worker 		seek_info.mean += (nseeks * mean);
434*1a3d31e3SAndroid Build Coastguard Worker 		seek_info.median += (nseeks * median);
435*1a3d31e3SAndroid Build Coastguard Worker 		add_seek_mode_info(&seek_info, &m);
436*1a3d31e3SAndroid Build Coastguard Worker 		free(m.modes);
437*1a3d31e3SAndroid Build Coastguard Worker 	}
438*1a3d31e3SAndroid Build Coastguard Worker }
439*1a3d31e3SAndroid Build Coastguard Worker 
__output_dip_seek_info(struct d_info * dip,void * arg)440*1a3d31e3SAndroid Build Coastguard Worker void __output_dip_seek_info(struct d_info *dip, void *arg)
441*1a3d31e3SAndroid Build Coastguard Worker {
442*1a3d31e3SAndroid Build Coastguard Worker 	do_output_dip_seek_info(dip, (FILE *)arg, 0);
443*1a3d31e3SAndroid Build Coastguard Worker }
444*1a3d31e3SAndroid Build Coastguard Worker 
__output_dip_q2q_seek_info(struct d_info * dip,void * arg)445*1a3d31e3SAndroid Build Coastguard Worker void __output_dip_q2q_seek_info(struct d_info *dip, void *arg)
446*1a3d31e3SAndroid Build Coastguard Worker {
447*1a3d31e3SAndroid Build Coastguard Worker 	do_output_dip_seek_info(dip, (FILE *)arg, 1);
448*1a3d31e3SAndroid Build Coastguard Worker }
449*1a3d31e3SAndroid Build Coastguard Worker 
output_dip_seek_info(FILE * ofp)450*1a3d31e3SAndroid Build Coastguard Worker void output_dip_seek_info(FILE *ofp)
451*1a3d31e3SAndroid Build Coastguard Worker {
452*1a3d31e3SAndroid Build Coastguard Worker 	n_seeks = 1;
453*1a3d31e3SAndroid Build Coastguard Worker 	memset(&seek_info, 0, sizeof(seek_info));
454*1a3d31e3SAndroid Build Coastguard Worker 
455*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "%10s | %15s %15s %15s | %-15s\n", "DEV", "NSEEKS",
456*1a3d31e3SAndroid Build Coastguard Worker 			"MEAN", "MEDIAN", "MODE");
457*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "---------- | --------------- --------------- --------------- | ---------------\n");
458*1a3d31e3SAndroid Build Coastguard Worker 	dip_foreach_out(__output_dip_seek_info, ofp);
459*1a3d31e3SAndroid Build Coastguard Worker 	if (n_seeks > 1) {
460*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(ofp, "---------- | --------------- --------------- --------------- | ---------------\n");
461*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(ofp, "%10s | %15s %15s %15s | %-15s\n",
462*1a3d31e3SAndroid Build Coastguard Worker 		        "Overall", "NSEEKS", "MEAN", "MEDIAN", "MODE");
463*1a3d31e3SAndroid Build Coastguard Worker 		output_seek_mode_info(ofp, &seek_info);
464*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(ofp, "\n");
465*1a3d31e3SAndroid Build Coastguard Worker 	}
466*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "\n");
467*1a3d31e3SAndroid Build Coastguard Worker }
468*1a3d31e3SAndroid Build Coastguard Worker 
output_dip_q2q_seek_info(FILE * ofp)469*1a3d31e3SAndroid Build Coastguard Worker void output_dip_q2q_seek_info(FILE *ofp)
470*1a3d31e3SAndroid Build Coastguard Worker {
471*1a3d31e3SAndroid Build Coastguard Worker 	n_seeks = 1;
472*1a3d31e3SAndroid Build Coastguard Worker 	memset(&seek_info, 0, sizeof(seek_info));
473*1a3d31e3SAndroid Build Coastguard Worker 
474*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "%10s | %15s %15s %15s | %-15s\n", "DEV", "NSEEKS",
475*1a3d31e3SAndroid Build Coastguard Worker 			"MEAN", "MEDIAN", "MODE");
476*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "---------- | --------------- --------------- --------------- | ---------------\n");
477*1a3d31e3SAndroid Build Coastguard Worker 	dip_foreach_out(__output_dip_q2q_seek_info, ofp);
478*1a3d31e3SAndroid Build Coastguard Worker 	if (n_seeks > 1) {
479*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(ofp, "---------- | --------------- --------------- --------------- | ---------------\n");
480*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(ofp, "%10s | %15s %15s %15s | %-15s\n",
481*1a3d31e3SAndroid Build Coastguard Worker 		        "Overall", "NSEEKS", "MEAN", "MEDIAN", "MODE");
482*1a3d31e3SAndroid Build Coastguard Worker 		output_seek_mode_info(ofp, &seek_info);
483*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(ofp, "\n");
484*1a3d31e3SAndroid Build Coastguard Worker 	}
485*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "\n");
486*1a3d31e3SAndroid Build Coastguard Worker }
487*1a3d31e3SAndroid Build Coastguard Worker 
488*1a3d31e3SAndroid Build Coastguard Worker struct __opa {
489*1a3d31e3SAndroid Build Coastguard Worker 	FILE *ofp;
490*1a3d31e3SAndroid Build Coastguard Worker 	ai_pip_t (*func)(struct p_info *);
491*1a3d31e3SAndroid Build Coastguard Worker };
492*1a3d31e3SAndroid Build Coastguard Worker 
__output_pip_avg(struct p_info * pip,void * arg)493*1a3d31e3SAndroid Build Coastguard Worker void __output_pip_avg(struct p_info *pip, void *arg)
494*1a3d31e3SAndroid Build Coastguard Worker {
495*1a3d31e3SAndroid Build Coastguard Worker 	struct __opa *opap = arg;
496*1a3d31e3SAndroid Build Coastguard Worker 	ai_pip_t ap = opap->func(pip);
497*1a3d31e3SAndroid Build Coastguard Worker 
498*1a3d31e3SAndroid Build Coastguard Worker 	if (ap->n > 0) {
499*1a3d31e3SAndroid Build Coastguard Worker 		char proc_name[15];
500*1a3d31e3SAndroid Build Coastguard Worker 		snprintf(proc_name, 15, "%s", pip->name);
501*1a3d31e3SAndroid Build Coastguard Worker 
502*1a3d31e3SAndroid Build Coastguard Worker 		ap->avg = BIT_TIME(ap->total) / (double)ap->n;
503*1a3d31e3SAndroid Build Coastguard Worker 		__output_avg(opap->ofp, proc_name, ap, 0);
504*1a3d31e3SAndroid Build Coastguard Worker 	}
505*1a3d31e3SAndroid Build Coastguard Worker }
506*1a3d31e3SAndroid Build Coastguard Worker 
output_pip_avg(FILE * ofp,char * hdr,ai_pip_t (* func)(struct p_info *))507*1a3d31e3SAndroid Build Coastguard Worker void output_pip_avg(FILE *ofp, char *hdr, ai_pip_t (*func)(struct p_info *))
508*1a3d31e3SAndroid Build Coastguard Worker {
509*1a3d31e3SAndroid Build Coastguard Worker 	struct __opa opa = { .ofp = ofp, .func = func };
510*1a3d31e3SAndroid Build Coastguard Worker 
511*1a3d31e3SAndroid Build Coastguard Worker 	output_hdr(ofp, hdr);
512*1a3d31e3SAndroid Build Coastguard Worker 	pip_foreach_out(__output_pip_avg, &opa);
513*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "\n");
514*1a3d31e3SAndroid Build Coastguard Worker }
515*1a3d31e3SAndroid Build Coastguard Worker 
516*1a3d31e3SAndroid Build Coastguard Worker int n_plugs;
517*1a3d31e3SAndroid Build Coastguard Worker struct plug_info {
518*1a3d31e3SAndroid Build Coastguard Worker 	long n_plugs, n_unplugs_t;
519*1a3d31e3SAndroid Build Coastguard Worker 	double t_percent;
520*1a3d31e3SAndroid Build Coastguard Worker } plug_info;
521*1a3d31e3SAndroid Build Coastguard Worker 
__dip_output_plug(struct d_info * dip,void * arg)522*1a3d31e3SAndroid Build Coastguard Worker void __dip_output_plug(struct d_info *dip, void *arg)
523*1a3d31e3SAndroid Build Coastguard Worker {
524*1a3d31e3SAndroid Build Coastguard Worker 	char dev_info[15];
525*1a3d31e3SAndroid Build Coastguard Worker 	FILE *ofp = arg;
526*1a3d31e3SAndroid Build Coastguard Worker 	double delta, pct;
527*1a3d31e3SAndroid Build Coastguard Worker 
528*1a3d31e3SAndroid Build Coastguard Worker 	if (dip->is_plugged)
529*1a3d31e3SAndroid Build Coastguard Worker 		dip_unplug(dip->device, dip->end_time, 0);
530*1a3d31e3SAndroid Build Coastguard Worker 	if ((dip->nplugs + dip->nplugs_t) > 0) {
531*1a3d31e3SAndroid Build Coastguard Worker 		delta = dip->end_time - dip->start_time;
532*1a3d31e3SAndroid Build Coastguard Worker 		pct = 100.0 * (dip->plugged_time / delta);
533*1a3d31e3SAndroid Build Coastguard Worker 
534*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(ofp, "%10s | %10d(%10d) | %13.9lf%%\n",
535*1a3d31e3SAndroid Build Coastguard Worker 			make_dev_hdr(dev_info, 15, dip, 1),
536*1a3d31e3SAndroid Build Coastguard Worker 			dip->nplugs, dip->nplugs_t, pct);
537*1a3d31e3SAndroid Build Coastguard Worker 
538*1a3d31e3SAndroid Build Coastguard Worker 		if (easy_parse_avgs) {
539*1a3d31e3SAndroid Build Coastguard Worker 			fprintf(xavgs_ofp,
540*1a3d31e3SAndroid Build Coastguard Worker 				"PLG %s %d %d %.9lf\n",
541*1a3d31e3SAndroid Build Coastguard Worker 				make_dev_hdr(dev_info, 15, dip, 0),
542*1a3d31e3SAndroid Build Coastguard Worker 				dip->nplugs, dip->nplugs_t, pct);
543*1a3d31e3SAndroid Build Coastguard Worker 		}
544*1a3d31e3SAndroid Build Coastguard Worker 
545*1a3d31e3SAndroid Build Coastguard Worker 		n_plugs++;
546*1a3d31e3SAndroid Build Coastguard Worker 		plug_info.n_plugs += dip->nplugs;
547*1a3d31e3SAndroid Build Coastguard Worker 		plug_info.n_unplugs_t += dip->nplugs_t;
548*1a3d31e3SAndroid Build Coastguard Worker 		plug_info.t_percent += pct;
549*1a3d31e3SAndroid Build Coastguard Worker 	}
550*1a3d31e3SAndroid Build Coastguard Worker }
551*1a3d31e3SAndroid Build Coastguard Worker 
__dip_output_plug_all(FILE * ofp,struct plug_info * p)552*1a3d31e3SAndroid Build Coastguard Worker void __dip_output_plug_all(FILE *ofp, struct plug_info *p)
553*1a3d31e3SAndroid Build Coastguard Worker {
554*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "---------- | ---------- ----------  | ----------------\n");
555*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "%10s | %10s %10s  | %s\n",
556*1a3d31e3SAndroid Build Coastguard Worker 	        "Overall", "# Plugs", "# Timer Us", "% Time Q Plugged");
557*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "%10s | %10ld(%10ld) | %13.9lf%%\n", "Average",
558*1a3d31e3SAndroid Build Coastguard Worker 	        p->n_plugs / n_plugs, p->n_unplugs_t / n_plugs,
559*1a3d31e3SAndroid Build Coastguard Worker 		p->t_percent / n_plugs);
560*1a3d31e3SAndroid Build Coastguard Worker 
561*1a3d31e3SAndroid Build Coastguard Worker }
562*1a3d31e3SAndroid Build Coastguard Worker 
563*1a3d31e3SAndroid Build Coastguard Worker __u64 n_nios_uplugs, n_nios_uplugs_t;
564*1a3d31e3SAndroid Build Coastguard Worker struct nios_plug_info {
565*1a3d31e3SAndroid Build Coastguard Worker 	__u64 tot_nios_up, tot_nios_up_t;
566*1a3d31e3SAndroid Build Coastguard Worker } nios_plug_info;
567*1a3d31e3SAndroid Build Coastguard Worker 
__dip_output_plug_nios(struct d_info * dip,void * arg)568*1a3d31e3SAndroid Build Coastguard Worker void __dip_output_plug_nios(struct d_info *dip, void *arg)
569*1a3d31e3SAndroid Build Coastguard Worker {
570*1a3d31e3SAndroid Build Coastguard Worker 	char dev_info[15];
571*1a3d31e3SAndroid Build Coastguard Worker 	FILE *ofp = arg;
572*1a3d31e3SAndroid Build Coastguard Worker 	double a_nios_uplug = 0.0, a_nios_uplug_t = 0.0;
573*1a3d31e3SAndroid Build Coastguard Worker 
574*1a3d31e3SAndroid Build Coastguard Worker 	if (dip->nios_up && dip->nplugs) {
575*1a3d31e3SAndroid Build Coastguard Worker 		a_nios_uplug = (double)dip->nios_up / (double)dip->nplugs;
576*1a3d31e3SAndroid Build Coastguard Worker 		n_nios_uplugs += dip->nplugs;
577*1a3d31e3SAndroid Build Coastguard Worker 		nios_plug_info.tot_nios_up += dip->nios_up;
578*1a3d31e3SAndroid Build Coastguard Worker 	}
579*1a3d31e3SAndroid Build Coastguard Worker 	if (dip->nios_upt && dip->nplugs_t) {
580*1a3d31e3SAndroid Build Coastguard Worker 		a_nios_uplug_t = (double)dip->nios_upt / (double)dip->nplugs_t;
581*1a3d31e3SAndroid Build Coastguard Worker 		n_nios_uplugs_t += dip->nplugs_t;
582*1a3d31e3SAndroid Build Coastguard Worker 		nios_plug_info.tot_nios_up_t += dip->nios_upt;
583*1a3d31e3SAndroid Build Coastguard Worker 	}
584*1a3d31e3SAndroid Build Coastguard Worker 
585*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "%10s | %10.1lf   %10.1lf\n",
586*1a3d31e3SAndroid Build Coastguard Worker 		make_dev_hdr(dev_info, 15, dip, 1),
587*1a3d31e3SAndroid Build Coastguard Worker 		a_nios_uplug, a_nios_uplug_t);
588*1a3d31e3SAndroid Build Coastguard Worker 
589*1a3d31e3SAndroid Build Coastguard Worker 	if (easy_parse_avgs) {
590*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(xavgs_ofp,
591*1a3d31e3SAndroid Build Coastguard Worker 			"UPG %s %.9lf %.9lf\n",
592*1a3d31e3SAndroid Build Coastguard Worker 			make_dev_hdr(dev_info, 15, dip, 0),
593*1a3d31e3SAndroid Build Coastguard Worker 			a_nios_uplug, a_nios_uplug_t);
594*1a3d31e3SAndroid Build Coastguard Worker 	}
595*1a3d31e3SAndroid Build Coastguard Worker }
596*1a3d31e3SAndroid Build Coastguard Worker 
__dip_output_uplug_all(FILE * ofp,struct nios_plug_info * p)597*1a3d31e3SAndroid Build Coastguard Worker void __dip_output_uplug_all(FILE *ofp, struct nios_plug_info *p)
598*1a3d31e3SAndroid Build Coastguard Worker {
599*1a3d31e3SAndroid Build Coastguard Worker 	double ios_unp = 0.0, ios_unp_to = 0.0;
600*1a3d31e3SAndroid Build Coastguard Worker 
601*1a3d31e3SAndroid Build Coastguard Worker 	if (n_nios_uplugs)
602*1a3d31e3SAndroid Build Coastguard Worker 		ios_unp = (double)p->tot_nios_up / (double)n_nios_uplugs;
603*1a3d31e3SAndroid Build Coastguard Worker 	if (n_nios_uplugs_t)
604*1a3d31e3SAndroid Build Coastguard Worker 		ios_unp_to = (double)p->tot_nios_up_t / (double)n_nios_uplugs_t;
605*1a3d31e3SAndroid Build Coastguard Worker 
606*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "---------- | ----------   ----------\n");
607*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "%10s | %10s   %10s\n",
608*1a3d31e3SAndroid Build Coastguard Worker 		"Overall", "IOs/Unp", "IOs/Unp(to)");
609*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "%10s | %10.1lf   %10.1lf\n",
610*1a3d31e3SAndroid Build Coastguard Worker 		"Average", ios_unp, ios_unp_to);
611*1a3d31e3SAndroid Build Coastguard Worker }
612*1a3d31e3SAndroid Build Coastguard Worker 
output_plug_info(FILE * ofp)613*1a3d31e3SAndroid Build Coastguard Worker void output_plug_info(FILE *ofp)
614*1a3d31e3SAndroid Build Coastguard Worker {
615*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "%10s | %10s %10s  | %s\n",
616*1a3d31e3SAndroid Build Coastguard Worker 	        "DEV", "# Plugs", "# Timer Us", "% Time Q Plugged");
617*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "---------- | ---------- ----------  | ----------------\n");
618*1a3d31e3SAndroid Build Coastguard Worker 	dip_foreach_out(__dip_output_plug, ofp);
619*1a3d31e3SAndroid Build Coastguard Worker 	if (n_plugs > 1)
620*1a3d31e3SAndroid Build Coastguard Worker 		__dip_output_plug_all(ofp, &plug_info);
621*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "\n");
622*1a3d31e3SAndroid Build Coastguard Worker 
623*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "%10s | %10s   %10s\n",
624*1a3d31e3SAndroid Build Coastguard Worker 		"DEV", "IOs/Unp", "IOs/Unp(to)");
625*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "---------- | ----------   ----------\n");
626*1a3d31e3SAndroid Build Coastguard Worker 	dip_foreach_out(__dip_output_plug_nios, ofp);
627*1a3d31e3SAndroid Build Coastguard Worker 	if (n_nios_uplugs || n_nios_uplugs_t)
628*1a3d31e3SAndroid Build Coastguard Worker 		__dip_output_uplug_all(ofp, &nios_plug_info);
629*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "\n");
630*1a3d31e3SAndroid Build Coastguard Worker }
631*1a3d31e3SAndroid Build Coastguard Worker 
632*1a3d31e3SAndroid Build Coastguard Worker int n_actQs;
633*1a3d31e3SAndroid Build Coastguard Worker struct actQ_info {
634*1a3d31e3SAndroid Build Coastguard Worker 	__u64 t_qs;
635*1a3d31e3SAndroid Build Coastguard Worker 	__u64 t_act_qs;
636*1a3d31e3SAndroid Build Coastguard Worker } actQ_info;
637*1a3d31e3SAndroid Build Coastguard Worker 
__dip_output_actQ(struct d_info * dip,void * arg)638*1a3d31e3SAndroid Build Coastguard Worker void __dip_output_actQ(struct d_info *dip, void *arg)
639*1a3d31e3SAndroid Build Coastguard Worker {
640*1a3d31e3SAndroid Build Coastguard Worker 	if (dip->n_qs > 0 && !remapper_dev(dip->device)) {
641*1a3d31e3SAndroid Build Coastguard Worker 		char dev_info[15];
642*1a3d31e3SAndroid Build Coastguard Worker 		double a_actQs = (double)dip->t_act_q / (double)dip->n_qs;
643*1a3d31e3SAndroid Build Coastguard Worker 
644*1a3d31e3SAndroid Build Coastguard Worker 		fprintf((FILE *)arg, "%10s | %13.1lf\n",
645*1a3d31e3SAndroid Build Coastguard Worker 			make_dev_hdr(dev_info, 15, dip, 1), a_actQs);
646*1a3d31e3SAndroid Build Coastguard Worker 
647*1a3d31e3SAndroid Build Coastguard Worker 		if (easy_parse_avgs) {
648*1a3d31e3SAndroid Build Coastguard Worker 			fprintf(xavgs_ofp,
649*1a3d31e3SAndroid Build Coastguard Worker 				"ARQ %s %.9lf\n",
650*1a3d31e3SAndroid Build Coastguard Worker 				make_dev_hdr(dev_info, 15, dip, 0), a_actQs);
651*1a3d31e3SAndroid Build Coastguard Worker 		}
652*1a3d31e3SAndroid Build Coastguard Worker 
653*1a3d31e3SAndroid Build Coastguard Worker 		n_actQs++;
654*1a3d31e3SAndroid Build Coastguard Worker 		actQ_info.t_qs += dip->n_qs;
655*1a3d31e3SAndroid Build Coastguard Worker 		actQ_info.t_act_qs += dip->t_act_q;
656*1a3d31e3SAndroid Build Coastguard Worker 	}
657*1a3d31e3SAndroid Build Coastguard Worker }
658*1a3d31e3SAndroid Build Coastguard Worker 
__dip_output_actQ_all(FILE * ofp,struct actQ_info * p)659*1a3d31e3SAndroid Build Coastguard Worker void __dip_output_actQ_all(FILE *ofp, struct actQ_info *p)
660*1a3d31e3SAndroid Build Coastguard Worker {
661*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "---------- | -------------\n");
662*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "%10s | %13s\n", "Overall", "Avgs Reqs @ Q");
663*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "%10s | %13.1lf\n", "Average",
664*1a3d31e3SAndroid Build Coastguard Worker 		(double)p->t_act_qs / (double)p->t_qs);
665*1a3d31e3SAndroid Build Coastguard Worker }
666*1a3d31e3SAndroid Build Coastguard Worker 
output_actQ_info(FILE * ofp)667*1a3d31e3SAndroid Build Coastguard Worker void output_actQ_info(FILE *ofp)
668*1a3d31e3SAndroid Build Coastguard Worker {
669*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "%10s | %13s\n", "DEV", "Avg Reqs @ Q");
670*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "---------- | -------------\n");
671*1a3d31e3SAndroid Build Coastguard Worker 	dip_foreach_out(__dip_output_actQ, ofp);
672*1a3d31e3SAndroid Build Coastguard Worker 	if (n_actQs > 1)
673*1a3d31e3SAndroid Build Coastguard Worker 		__dip_output_actQ_all(ofp, &actQ_info);
674*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "\n");
675*1a3d31e3SAndroid Build Coastguard Worker }
676*1a3d31e3SAndroid Build Coastguard Worker 
__dip_output_p_live(struct d_info * dip,void * arg)677*1a3d31e3SAndroid Build Coastguard Worker void __dip_output_p_live(struct d_info *dip, void *arg)
678*1a3d31e3SAndroid Build Coastguard Worker {
679*1a3d31e3SAndroid Build Coastguard Worker 	char dev_info[15];
680*1a3d31e3SAndroid Build Coastguard Worker 	FILE *ofp = arg;
681*1a3d31e3SAndroid Build Coastguard Worker 	char *ttl = dip ? make_dev_hdr(dev_info, 15, dip, 1) : "Total Sys";
682*1a3d31e3SAndroid Build Coastguard Worker 	struct p_live_info *plip = p_live_get(dip, base_y);
683*1a3d31e3SAndroid Build Coastguard Worker 
684*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "%10s | %10lu %13.9lf %13.9lf %6.2lf\n", ttl,
685*1a3d31e3SAndroid Build Coastguard Worker 		plip->nlives, plip->avg_live, plip->avg_lull, plip->p_live);
686*1a3d31e3SAndroid Build Coastguard Worker 	if (plip->nlives)
687*1a3d31e3SAndroid Build Coastguard Worker 		base_y += 1;
688*1a3d31e3SAndroid Build Coastguard Worker }
689*1a3d31e3SAndroid Build Coastguard Worker 
output_p_live(FILE * ofp)690*1a3d31e3SAndroid Build Coastguard Worker void output_p_live(FILE *ofp)
691*1a3d31e3SAndroid Build Coastguard Worker {
692*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "%10s | %10s %13s %13s %6s\n", "DEV",
693*1a3d31e3SAndroid Build Coastguard Worker 		"# Live", "Avg. Act", "Avg. !Act", "% Live");
694*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "---------- | ---------- "
695*1a3d31e3SAndroid Build Coastguard Worker 		     "------------- ------------- ------\n");
696*1a3d31e3SAndroid Build Coastguard Worker 	base_y = 1;
697*1a3d31e3SAndroid Build Coastguard Worker 	dip_foreach_out(__dip_output_p_live, ofp);
698*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "---------- | ---------- "
699*1a3d31e3SAndroid Build Coastguard Worker 		     "------------- ------------- ------\n");
700*1a3d31e3SAndroid Build Coastguard Worker 	base_y = 0;
701*1a3d31e3SAndroid Build Coastguard Worker 	__dip_output_p_live(NULL, ofp);
702*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "\n");
703*1a3d31e3SAndroid Build Coastguard Worker }
704*1a3d31e3SAndroid Build Coastguard Worker 
output_histos(void)705*1a3d31e3SAndroid Build Coastguard Worker void output_histos(void)
706*1a3d31e3SAndroid Build Coastguard Worker {
707*1a3d31e3SAndroid Build Coastguard Worker 	int i;
708*1a3d31e3SAndroid Build Coastguard Worker 	FILE *ofp;
709*1a3d31e3SAndroid Build Coastguard Worker 	char fname[256];
710*1a3d31e3SAndroid Build Coastguard Worker 
711*1a3d31e3SAndroid Build Coastguard Worker 	if (output_name == NULL) return;
712*1a3d31e3SAndroid Build Coastguard Worker 
713*1a3d31e3SAndroid Build Coastguard Worker 	sprintf(fname, "%s_qhist.dat", output_name);
714*1a3d31e3SAndroid Build Coastguard Worker 	ofp = my_fopen(fname, "w");
715*1a3d31e3SAndroid Build Coastguard Worker 	if (!ofp) {
716*1a3d31e3SAndroid Build Coastguard Worker 		perror(fname);
717*1a3d31e3SAndroid Build Coastguard Worker 		return;
718*1a3d31e3SAndroid Build Coastguard Worker 	}
719*1a3d31e3SAndroid Build Coastguard Worker 
720*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "# BTT histogram data\n");
721*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "# Q buckets\n");
722*1a3d31e3SAndroid Build Coastguard Worker 	for (i = 0; i < (N_HIST_BKTS-1); i++)
723*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(ofp, "%4d %lld\n", (i+1), (long long)q_histo[i]);
724*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "\n# Q bucket for > %d\n%4d %lld\n", (int)N_HIST_BKTS-1,
725*1a3d31e3SAndroid Build Coastguard Worker 		N_HIST_BKTS-1, (long long)q_histo[N_HIST_BKTS-1]);
726*1a3d31e3SAndroid Build Coastguard Worker 	fclose(ofp);
727*1a3d31e3SAndroid Build Coastguard Worker 
728*1a3d31e3SAndroid Build Coastguard Worker 	sprintf(fname, "%s_dhist.dat", output_name);
729*1a3d31e3SAndroid Build Coastguard Worker 	ofp = my_fopen(fname, "w");
730*1a3d31e3SAndroid Build Coastguard Worker 	if (!ofp) {
731*1a3d31e3SAndroid Build Coastguard Worker 		perror(fname);
732*1a3d31e3SAndroid Build Coastguard Worker 		return;
733*1a3d31e3SAndroid Build Coastguard Worker 	}
734*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "# D buckets\n");
735*1a3d31e3SAndroid Build Coastguard Worker 	for (i = 0; i < (N_HIST_BKTS-1); i++)
736*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(ofp, "%4d %lld\n", (i+1), (long long)d_histo[i]);
737*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "\n# D bucket for > %d\n%4d %lld\n", (int)N_HIST_BKTS-1,
738*1a3d31e3SAndroid Build Coastguard Worker 		N_HIST_BKTS-1, (long long)d_histo[N_HIST_BKTS-1]);
739*1a3d31e3SAndroid Build Coastguard Worker 	fclose(ofp);
740*1a3d31e3SAndroid Build Coastguard Worker }
741*1a3d31e3SAndroid Build Coastguard Worker 
output_avgs(FILE * ofp)742*1a3d31e3SAndroid Build Coastguard Worker int output_avgs(FILE *ofp)
743*1a3d31e3SAndroid Build Coastguard Worker {
744*1a3d31e3SAndroid Build Coastguard Worker 	if (output_all_data) {
745*1a3d31e3SAndroid Build Coastguard Worker 		if (exes == NULL || *exes != '\0') {
746*1a3d31e3SAndroid Build Coastguard Worker 			output_section_hdr(ofp, "Per Process");
747*1a3d31e3SAndroid Build Coastguard Worker 			output_pip_avg(ofp, "Q2Qdm", pip_q2q_dm_avg);
748*1a3d31e3SAndroid Build Coastguard Worker 			output_pip_avg(ofp, "Q2Adm", pip_q2a_dm_avg);
749*1a3d31e3SAndroid Build Coastguard Worker 			output_pip_avg(ofp, "Q2Cdm", pip_q2c_dm_avg);
750*1a3d31e3SAndroid Build Coastguard Worker 			fprintf(ofp, "\n");
751*1a3d31e3SAndroid Build Coastguard Worker 
752*1a3d31e3SAndroid Build Coastguard Worker 			output_pip_avg(ofp, "Q2Q", pip_q2q_avg);
753*1a3d31e3SAndroid Build Coastguard Worker 			output_pip_avg(ofp, "Q2A", pip_q2a_avg);
754*1a3d31e3SAndroid Build Coastguard Worker 			output_pip_avg(ofp, "Q2G", pip_q2g_avg);
755*1a3d31e3SAndroid Build Coastguard Worker 			output_pip_avg(ofp, "S2G", pip_s2g_avg);
756*1a3d31e3SAndroid Build Coastguard Worker 			output_pip_avg(ofp, "G2I", pip_g2i_avg);
757*1a3d31e3SAndroid Build Coastguard Worker 			output_pip_avg(ofp, "Q2M", pip_q2m_avg);
758*1a3d31e3SAndroid Build Coastguard Worker 			output_pip_avg(ofp, "I2D", pip_i2d_avg);
759*1a3d31e3SAndroid Build Coastguard Worker 			output_pip_avg(ofp, "D2C", pip_d2c_avg);
760*1a3d31e3SAndroid Build Coastguard Worker 			output_pip_avg(ofp, "Q2C", pip_q2c_avg);
761*1a3d31e3SAndroid Build Coastguard Worker 		}
762*1a3d31e3SAndroid Build Coastguard Worker 
763*1a3d31e3SAndroid Build Coastguard Worker 		output_section_hdr(ofp, "Per Device");
764*1a3d31e3SAndroid Build Coastguard Worker 		output_dip_avg(ofp, "Q2Qdm", dip_q2q_dm_avg);
765*1a3d31e3SAndroid Build Coastguard Worker 		output_dip_avg(ofp, "Q2Adm", dip_q2a_dm_avg);
766*1a3d31e3SAndroid Build Coastguard Worker 		output_dip_avg(ofp, "Q2Cdm", dip_q2c_dm_avg);
767*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(ofp, "\n");
768*1a3d31e3SAndroid Build Coastguard Worker 
769*1a3d31e3SAndroid Build Coastguard Worker 		output_dip_avg(ofp, "Q2Q", dip_q2q_avg);
770*1a3d31e3SAndroid Build Coastguard Worker 		output_dip_avg(ofp, "Q2A", dip_q2a_avg);
771*1a3d31e3SAndroid Build Coastguard Worker 		output_dip_avg(ofp, "Q2G", dip_q2g_avg);
772*1a3d31e3SAndroid Build Coastguard Worker 		output_dip_avg(ofp, "S2G", dip_s2g_avg);
773*1a3d31e3SAndroid Build Coastguard Worker 		output_dip_avg(ofp, "G2I", dip_g2i_avg);
774*1a3d31e3SAndroid Build Coastguard Worker 		output_dip_avg(ofp, "Q2M", dip_q2m_avg);
775*1a3d31e3SAndroid Build Coastguard Worker 		output_dip_avg(ofp, "I2D", dip_i2d_avg);
776*1a3d31e3SAndroid Build Coastguard Worker 		output_dip_avg(ofp, "D2C", dip_d2c_avg);
777*1a3d31e3SAndroid Build Coastguard Worker 		output_dip_avg(ofp, "Q2C", dip_q2c_avg);
778*1a3d31e3SAndroid Build Coastguard Worker 	}
779*1a3d31e3SAndroid Build Coastguard Worker 
780*1a3d31e3SAndroid Build Coastguard Worker 	output_section_hdr(ofp, "All Devices");
781*1a3d31e3SAndroid Build Coastguard Worker 	output_hdr(ofp, "ALL");
782*1a3d31e3SAndroid Build Coastguard Worker 	__output_avg(ofp, "Q2Qdm", &all_avgs.q2q_dm, 0);
783*1a3d31e3SAndroid Build Coastguard Worker 	__output_avg(ofp, "Q2Adm", &all_avgs.q2a_dm, 0);
784*1a3d31e3SAndroid Build Coastguard Worker 	__output_avg(ofp, "Q2Cdm", &all_avgs.q2c_dm, 0);
785*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "\n");
786*1a3d31e3SAndroid Build Coastguard Worker 
787*1a3d31e3SAndroid Build Coastguard Worker 	__output_avg(ofp, "Q2Q", &all_avgs.q2q, 1);
788*1a3d31e3SAndroid Build Coastguard Worker 	__output_avg(ofp, "Q2A", &all_avgs.q2a, 1);
789*1a3d31e3SAndroid Build Coastguard Worker 	__output_avg(ofp, "Q2G", &all_avgs.q2g, 1);
790*1a3d31e3SAndroid Build Coastguard Worker 	__output_avg(ofp, "S2G", &all_avgs.s2g, 1);
791*1a3d31e3SAndroid Build Coastguard Worker 	__output_avg(ofp, "G2I", &all_avgs.g2i, 1);
792*1a3d31e3SAndroid Build Coastguard Worker 	__output_avg(ofp, "Q2M", &all_avgs.q2m, 1);
793*1a3d31e3SAndroid Build Coastguard Worker 	__output_avg(ofp, "I2D", &all_avgs.i2d, 1);
794*1a3d31e3SAndroid Build Coastguard Worker 	__output_avg(ofp, "M2D", &all_avgs.m2d, 1);
795*1a3d31e3SAndroid Build Coastguard Worker 	__output_avg(ofp, "D2C", &all_avgs.d2c, 1);
796*1a3d31e3SAndroid Build Coastguard Worker 	__output_avg(ofp, "Q2C", &all_avgs.q2c, 1);
797*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "\n");
798*1a3d31e3SAndroid Build Coastguard Worker 
799*1a3d31e3SAndroid Build Coastguard Worker 	output_section_hdr(ofp, "Device Overhead");
800*1a3d31e3SAndroid Build Coastguard Worker 	output_dip_prep_ohead(ofp);
801*1a3d31e3SAndroid Build Coastguard Worker 
802*1a3d31e3SAndroid Build Coastguard Worker 	output_section_hdr(ofp, "Device Merge Information");
803*1a3d31e3SAndroid Build Coastguard Worker 	output_dip_merge_ratio(ofp);
804*1a3d31e3SAndroid Build Coastguard Worker 
805*1a3d31e3SAndroid Build Coastguard Worker 	output_section_hdr(ofp, "Device Q2Q Seek Information");
806*1a3d31e3SAndroid Build Coastguard Worker 	output_dip_q2q_seek_info(ofp);
807*1a3d31e3SAndroid Build Coastguard Worker 
808*1a3d31e3SAndroid Build Coastguard Worker 	output_section_hdr(ofp, "Device D2D Seek Information");
809*1a3d31e3SAndroid Build Coastguard Worker 	output_dip_seek_info(ofp);
810*1a3d31e3SAndroid Build Coastguard Worker 
811*1a3d31e3SAndroid Build Coastguard Worker 	output_section_hdr(ofp, "Plug Information");
812*1a3d31e3SAndroid Build Coastguard Worker 	output_plug_info(ofp);
813*1a3d31e3SAndroid Build Coastguard Worker 
814*1a3d31e3SAndroid Build Coastguard Worker 	output_section_hdr(ofp, "Active Requests At Q Information");
815*1a3d31e3SAndroid Build Coastguard Worker 	output_actQ_info(ofp);
816*1a3d31e3SAndroid Build Coastguard Worker 
817*1a3d31e3SAndroid Build Coastguard Worker 	output_section_hdr(ofp, "I/O Active Period Information");
818*1a3d31e3SAndroid Build Coastguard Worker 	output_p_live(ofp);
819*1a3d31e3SAndroid Build Coastguard Worker 
820*1a3d31e3SAndroid Build Coastguard Worker 	output_histos();
821*1a3d31e3SAndroid Build Coastguard Worker 
822*1a3d31e3SAndroid Build Coastguard Worker 
823*1a3d31e3SAndroid Build Coastguard Worker 	if (output_all_data) {
824*1a3d31e3SAndroid Build Coastguard Worker 		output_section_hdr(ofp, "Q2D Histogram");
825*1a3d31e3SAndroid Build Coastguard Worker 		output_q2d_histo(ofp);
826*1a3d31e3SAndroid Build Coastguard Worker 	}
827*1a3d31e3SAndroid Build Coastguard Worker 
828*1a3d31e3SAndroid Build Coastguard Worker 	return 0;
829*1a3d31e3SAndroid Build Coastguard Worker }
830*1a3d31e3SAndroid Build Coastguard Worker 
__output_ranges(FILE * ofp,struct list_head * head_p,float base)831*1a3d31e3SAndroid Build Coastguard Worker void __output_ranges(FILE *ofp, struct list_head *head_p, float base)
832*1a3d31e3SAndroid Build Coastguard Worker {
833*1a3d31e3SAndroid Build Coastguard Worker 	struct range_info *rip;
834*1a3d31e3SAndroid Build Coastguard Worker 	struct list_head *p;
835*1a3d31e3SAndroid Build Coastguard Worker 	float limit = base + 0.4;
836*1a3d31e3SAndroid Build Coastguard Worker 
837*1a3d31e3SAndroid Build Coastguard Worker 	__list_for_each(p, head_p) {
838*1a3d31e3SAndroid Build Coastguard Worker 		rip = list_entry(p, struct range_info, head);
839*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(ofp, "%13.9lf %5.1f\n", BIT_TIME(rip->start), base);
840*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(ofp, "%13.9lf %5.1f\n", BIT_TIME(rip->start), limit);
841*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(ofp, "%13.9lf %5.1f\n", BIT_TIME(rip->end), limit);
842*1a3d31e3SAndroid Build Coastguard Worker 		fprintf(ofp, "%13.9lf %5.1f\n", BIT_TIME(rip->end), base);
843*1a3d31e3SAndroid Build Coastguard Worker 	}
844*1a3d31e3SAndroid Build Coastguard Worker }
845*1a3d31e3SAndroid Build Coastguard Worker 
output_regions(FILE * ofp,char * header,struct region_info * reg,float base)846*1a3d31e3SAndroid Build Coastguard Worker int output_regions(FILE *ofp, char *header, struct region_info *reg,
847*1a3d31e3SAndroid Build Coastguard Worker 			  float base)
848*1a3d31e3SAndroid Build Coastguard Worker {
849*1a3d31e3SAndroid Build Coastguard Worker 	if (list_len(&reg->qranges) == 0 && list_len(&reg->cranges) == 0)
850*1a3d31e3SAndroid Build Coastguard Worker 		return 0;
851*1a3d31e3SAndroid Build Coastguard Worker 
852*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "# %16s : q activity\n", header);
853*1a3d31e3SAndroid Build Coastguard Worker 	__output_ranges(ofp, &reg->qranges, base);
854*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "\n");
855*1a3d31e3SAndroid Build Coastguard Worker 
856*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "# %16s : c activity\n", header);
857*1a3d31e3SAndroid Build Coastguard Worker 	__output_ranges(ofp, &reg->cranges, base + 0.5);
858*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "\n");
859*1a3d31e3SAndroid Build Coastguard Worker 
860*1a3d31e3SAndroid Build Coastguard Worker 	return 1;
861*1a3d31e3SAndroid Build Coastguard Worker }
862*1a3d31e3SAndroid Build Coastguard Worker 
863*1a3d31e3SAndroid Build Coastguard Worker struct __od {
864*1a3d31e3SAndroid Build Coastguard Worker 	FILE *ofp;
865*1a3d31e3SAndroid Build Coastguard Worker 	float base;
866*1a3d31e3SAndroid Build Coastguard Worker };
__output_dev(struct d_info * dip,void * arg)867*1a3d31e3SAndroid Build Coastguard Worker void __output_dev(struct d_info *dip, void *arg)
868*1a3d31e3SAndroid Build Coastguard Worker {
869*1a3d31e3SAndroid Build Coastguard Worker 	char header[128];
870*1a3d31e3SAndroid Build Coastguard Worker 	struct __od *odp = arg;
871*1a3d31e3SAndroid Build Coastguard Worker 
872*1a3d31e3SAndroid Build Coastguard Worker 	sprintf(header, "%d,%d", MAJOR(dip->device), MINOR(dip->device));
873*1a3d31e3SAndroid Build Coastguard Worker 	if (output_regions(odp->ofp, header, &dip->regions, odp->base))
874*1a3d31e3SAndroid Build Coastguard Worker 		odp->base += 1.0;
875*1a3d31e3SAndroid Build Coastguard Worker }
876*1a3d31e3SAndroid Build Coastguard Worker 
output_devs(FILE * ofp,float base)877*1a3d31e3SAndroid Build Coastguard Worker float output_devs(FILE *ofp, float base)
878*1a3d31e3SAndroid Build Coastguard Worker {
879*1a3d31e3SAndroid Build Coastguard Worker 	struct __od od = { .ofp = ofp, .base = base };
880*1a3d31e3SAndroid Build Coastguard Worker 
881*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "# Per device\n" );
882*1a3d31e3SAndroid Build Coastguard Worker 	dip_foreach_out(__output_dev, &od);
883*1a3d31e3SAndroid Build Coastguard Worker 	return od.base;
884*1a3d31e3SAndroid Build Coastguard Worker }
885*1a3d31e3SAndroid Build Coastguard Worker 
exe_match(char * exe,char * name)886*1a3d31e3SAndroid Build Coastguard Worker static inline int exe_match(char *exe, char *name)
887*1a3d31e3SAndroid Build Coastguard Worker {
888*1a3d31e3SAndroid Build Coastguard Worker 	return (exe == NULL) || (strstr(name, exe) != NULL);
889*1a3d31e3SAndroid Build Coastguard Worker }
890*1a3d31e3SAndroid Build Coastguard Worker 
891*1a3d31e3SAndroid Build Coastguard Worker struct __op {
892*1a3d31e3SAndroid Build Coastguard Worker 	FILE *ofp;
893*1a3d31e3SAndroid Build Coastguard Worker 	float base;
894*1a3d31e3SAndroid Build Coastguard Worker };
__output_procs(struct p_info * pip,void * arg)895*1a3d31e3SAndroid Build Coastguard Worker void __output_procs(struct p_info *pip, void *arg)
896*1a3d31e3SAndroid Build Coastguard Worker {
897*1a3d31e3SAndroid Build Coastguard Worker 	struct __op *opp = arg;
898*1a3d31e3SAndroid Build Coastguard Worker 	output_regions(opp->ofp, pip->name, &pip->regions, opp->base);
899*1a3d31e3SAndroid Build Coastguard Worker 	opp->base += 1.0;
900*1a3d31e3SAndroid Build Coastguard Worker }
901*1a3d31e3SAndroid Build Coastguard Worker 
output_procs(FILE * ofp,float base)902*1a3d31e3SAndroid Build Coastguard Worker float output_procs(FILE *ofp, float base)
903*1a3d31e3SAndroid Build Coastguard Worker {
904*1a3d31e3SAndroid Build Coastguard Worker 	struct __op op = { .ofp = ofp, .base = base };
905*1a3d31e3SAndroid Build Coastguard Worker 
906*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "# Per process\n" );
907*1a3d31e3SAndroid Build Coastguard Worker 	pip_foreach_out(__output_procs, &op);
908*1a3d31e3SAndroid Build Coastguard Worker 	return op.base;
909*1a3d31e3SAndroid Build Coastguard Worker }
910*1a3d31e3SAndroid Build Coastguard Worker 
output_ranges(FILE * ofp)911*1a3d31e3SAndroid Build Coastguard Worker int output_ranges(FILE *ofp)
912*1a3d31e3SAndroid Build Coastguard Worker {
913*1a3d31e3SAndroid Build Coastguard Worker 	float base = 0.0;
914*1a3d31e3SAndroid Build Coastguard Worker 
915*1a3d31e3SAndroid Build Coastguard Worker 	fprintf(ofp, "# %s\n", "Total System");
916*1a3d31e3SAndroid Build Coastguard Worker 	if (output_regions(ofp, "Total System", &all_regions, base))
917*1a3d31e3SAndroid Build Coastguard Worker 		base += 1.0;
918*1a3d31e3SAndroid Build Coastguard Worker 
919*1a3d31e3SAndroid Build Coastguard Worker 	if (n_devs > 1)
920*1a3d31e3SAndroid Build Coastguard Worker 		base = output_devs(ofp, base);
921*1a3d31e3SAndroid Build Coastguard Worker 
922*1a3d31e3SAndroid Build Coastguard Worker 	base = output_procs(ofp, base);
923*1a3d31e3SAndroid Build Coastguard Worker 
924*1a3d31e3SAndroid Build Coastguard Worker 	return 0;
925*1a3d31e3SAndroid Build Coastguard Worker }
926