1 /*
2  * Copyright © 2006 Mozilla Corporation
3  * Copyright © 2006 Red Hat, Inc.
4  *
5  * Permission to use, copy, modify, distribute, and sell this software
6  * and its documentation for any purpose is hereby granted without
7  * fee, provided that the above copyright notice appear in all copies
8  * and that both that copyright notice and this permission notice
9  * appear in supporting documentation, and that the name of
10  * the authors not be used in advertising or publicity pertaining to
11  * distribution of the software without specific, written prior
12  * permission. The authors make no representations about the
13  * suitability of this software for any purpose.  It is provided "as
14  * is" without express or implied warranty.
15  *
16  * THE AUTHORS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS
17  * SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
18  * FITNESS, IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY SPECIAL,
19  * INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER
20  * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
21  * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR
22  * IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
23  *
24  * Authors: Vladimir Vukicevic <vladimir@pobox.com>
25  *	    Carl Worth <cworth@cworth.org>
26  */
27 
28 #ifndef _CAIRO_PERF_H_
29 #define _CAIRO_PERF_H_
30 
31 #include "cairo-boilerplate.h"
32 #include "../src/cairo-time-private.h"
33 #include <stdio.h>
34 
35 typedef struct _cairo_stats {
36     cairo_time_t min_ticks;
37     cairo_time_t median_ticks;
38     double ticks_per_ms;
39     double std_dev;
40     int iterations;
41     cairo_time_t *values;
42 } cairo_stats_t;
43 
44 typedef struct _cairo_histogram {
45     int width, height, max_count;
46     int num_columns, num_rows;
47     cairo_time_t min_value, max_value;
48     int *columns;
49 } cairo_histogram_t;
50 
51 
52 /* timers */
53 
54 void
55 cairo_perf_timer_start (void);
56 
57 void
58 cairo_perf_timer_stop (void);
59 
60 typedef void
61 (*cairo_perf_timer_synchronize_t) (void *closure);
62 
63 void
64 cairo_perf_timer_set_synchronize (cairo_perf_timer_synchronize_t  synchronize,
65 				  void				 *closure);
66 
67 cairo_time_t
68 cairo_perf_timer_elapsed (void);
69 
70 /* yield */
71 
72 void
73 cairo_perf_yield (void);
74 
75 /* running a test case */
76 typedef struct _cairo_perf {
77     FILE *summary;
78     cairo_bool_t summary_continuous;
79 
80     /* Options from command-line */
81     unsigned int iterations;
82     cairo_bool_t exact_iterations;
83     cairo_bool_t raw;
84     cairo_bool_t list_only;
85     cairo_bool_t observe;
86     char **names;
87     unsigned int num_names;
88     char **exclude_names;
89     unsigned int num_exclude_names;
90     cairo_bool_t exact_names;
91 
92     double ms_per_iteration;
93     cairo_bool_t fast_and_sloppy;
94 
95     unsigned int tile_size;
96 
97     /* Stuff used internally */
98     cairo_time_t *times;
99     const cairo_boilerplate_target_t **targets;
100     int num_targets;
101     const cairo_boilerplate_target_t *target;
102     cairo_bool_t has_described_backend;
103     unsigned int test_number;
104     unsigned int size;
105     cairo_t *cr;
106 } cairo_perf_t;
107 
108 typedef cairo_time_t
109 (*cairo_perf_func_t) (cairo_t *cr, int width, int height, int loops);
110 
111 typedef double
112 (*cairo_count_func_t) (cairo_t *cr, int width, int height);
113 
114 cairo_bool_t
115 cairo_perf_can_run (cairo_perf_t *perf,
116 		    const char	 *name,
117 		    cairo_bool_t *is_explicit);
118 
119 void
120 cairo_perf_run (cairo_perf_t	   *perf,
121 		const char	   *name,
122 		cairo_perf_func_t   perf_func,
123 		cairo_count_func_t  count_func);
124 
125 void
126 cairo_perf_cover_sources_and_operators (cairo_perf_t	   *perf,
127 					const char	   *name,
128 					cairo_perf_func_t   perf_func,
129 					cairo_count_func_t  count_func);
130 
131 /* reporter convenience routines */
132 
133 typedef struct _test_report {
134     int id;
135     int fileno;
136     const char *configuration;
137     char *backend;
138     char *content;
139     char *name;
140     int size;
141 
142     /* The samples only exists for "raw" reports */
143     cairo_time_t *samples;
144     unsigned int samples_size;
145     unsigned int samples_count;
146 
147     /* The stats are either read directly or computed from samples.
148      * If the stats have not yet been computed from samples, then
149      * iterations will be 0. */
150     cairo_stats_t stats;
151 } test_report_t;
152 
153 typedef struct _test_diff {
154     test_report_t **tests;
155     int num_tests;
156     double min;
157     double max;
158     double change;
159 } test_diff_t;
160 
161 typedef struct _cairo_perf_report {
162     char *configuration;
163     const char *name;
164     int fileno;
165     test_report_t *tests;
166     int tests_size;
167     int tests_count;
168 } cairo_perf_report_t;
169 
170 typedef enum {
171     TEST_REPORT_STATUS_SUCCESS,
172     TEST_REPORT_STATUS_COMMENT,
173     TEST_REPORT_STATUS_ERROR
174 } test_report_status_t;
175 
176 void
177 cairo_perf_report_load (cairo_perf_report_t *report,
178 			const char *filename, int id,
179 			int (*cmp) (const void *, const void *));
180 
181 void
182 cairo_perf_report_sort_and_compute_stats (cairo_perf_report_t *report,
183 					  int (*cmp) (const void *, const void *));
184 
185 int
186 test_report_cmp_backend_then_name (const void *a,
187 				   const void *b);
188 
189 int
190 test_report_cmp_name (const void *a,
191 		      const void *b);
192 
193 #define CAIRO_PERF_ENABLED_DECL(func) cairo_bool_t (func ## _enabled) (cairo_perf_t *perf)
194 #define CAIRO_PERF_RUN_DECL(func) void (func) (cairo_perf_t *perf, cairo_t *cr, int width, int height)
195 
196 #define CAIRO_PERF_DECL(func) CAIRO_PERF_RUN_DECL(func); CAIRO_PERF_ENABLED_DECL(func)
197 
198 #ifndef MIN
199 #define MIN(a, b) ((a) < (b) ? (a) : (b))
200 #endif
201 
202 #ifndef MAX
203 #define MAX(a, b) ((a) > (b) ? (a) : (b))
204 #endif
205 
206 CAIRO_PERF_DECL (fill);
207 CAIRO_PERF_DECL (paint);
208 CAIRO_PERF_DECL (paint_with_alpha);
209 CAIRO_PERF_DECL (mask);
210 CAIRO_PERF_DECL (stroke);
211 CAIRO_PERF_DECL (subimage_copy);
212 CAIRO_PERF_DECL (disjoint);
213 CAIRO_PERF_DECL (hatching);
214 CAIRO_PERF_DECL (tessellate);
215 CAIRO_PERF_DECL (text);
216 CAIRO_PERF_DECL (glyphs);
217 CAIRO_PERF_DECL (hash_table);
218 CAIRO_PERF_DECL (pattern_create_radial);
219 CAIRO_PERF_DECL (zrusin);
220 CAIRO_PERF_DECL (world_map);
221 CAIRO_PERF_DECL (box_outline);
222 CAIRO_PERF_DECL (mosaic);
223 CAIRO_PERF_DECL (long_lines);
224 CAIRO_PERF_DECL (unaligned_clip);
225 CAIRO_PERF_DECL (rectangles);
226 CAIRO_PERF_DECL (rounded_rectangles);
227 CAIRO_PERF_DECL (long_dashed_lines);
228 CAIRO_PERF_DECL (composite_checker);
229 CAIRO_PERF_DECL (twin);
230 CAIRO_PERF_DECL (dragon);
231 CAIRO_PERF_DECL (pythagoras_tree);
232 CAIRO_PERF_DECL (intersections);
233 CAIRO_PERF_DECL (spiral);
234 CAIRO_PERF_DECL (wave);
235 CAIRO_PERF_DECL (many_strokes);
236 CAIRO_PERF_DECL (wide_strokes);
237 CAIRO_PERF_DECL (many_fills);
238 CAIRO_PERF_DECL (wide_fills);
239 CAIRO_PERF_DECL (many_curves);
240 CAIRO_PERF_DECL (curve);
241 CAIRO_PERF_DECL (a1_curve);
242 CAIRO_PERF_DECL (line);
243 CAIRO_PERF_DECL (a1_line);
244 CAIRO_PERF_DECL (pixel);
245 CAIRO_PERF_DECL (a1_pixel);
246 CAIRO_PERF_DECL (sierpinski);
247 CAIRO_PERF_DECL (fill_clip);
248 CAIRO_PERF_DECL (tiger);
249 
250 #endif
251