2 * Copyright © 2018 Broadcom
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
11 * The above copyright notice and this permission notice (including the next
12 * paragraph) shall be included in all copies or substantial portions of the
15 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
18 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
20 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
27 * Check consistency of some of the VC4 perf counters.
30 #define __STDC_FORMAT_MACROS
32 #include "piglit-util-gl.h"
34 PIGLIT_GL_TEST_CONFIG_BEGIN
36 config
.supports_gl_compat_version
= 20;
37 config
.window_visual
= PIGLIT_GL_VISUAL_RGB
;
39 PIGLIT_GL_TEST_CONFIG_END
43 printf("%s:%i\n", __func__, __LINE__); \
44 piglit_report_subtest_result(PIGLIT_FAIL, "%s", test->name); \
48 /******************************************************************************/
50 struct perfcounter_id
{
55 struct perfmon_counter
{
61 struct perfmon_group
{
65 int max_active_counters
;
66 struct perfmon_counter
*counters
;
71 struct perfmon_group
*groups
;
75 get_group_info(struct perfmon_group
*group
)
82 glGetPerfMonitorGroupStringAMD(group
->id
, 0, &length
, NULL
);
83 name
= calloc(length
+ 1, sizeof(char));
85 glGetPerfMonitorGroupStringAMD(group
->id
, length
+ 1, NULL
, name
);
87 glGetPerfMonitorCountersAMD(group
->id
, &group
->num_counters
,
89 group
->counters
= calloc(group
->num_counters
, sizeof(*group
->counters
));
90 counterids
= calloc(group
->num_counters
, sizeof(*counterids
));
91 glGetPerfMonitorCountersAMD(group
->id
, NULL
,
92 &group
->max_active_counters
,
93 group
->num_counters
, counterids
);
95 for (i
= 0; i
< group
->num_counters
; i
++) {
96 group
->counters
[i
].id
= counterids
[i
];
97 glGetPerfMonitorCounterStringAMD(group
->id
, counterids
[i
], 0,
99 name
= calloc(length
+ 1, sizeof(char));
100 group
->counters
[i
].name
= name
;
101 glGetPerfMonitorCounterStringAMD(group
->id
, counterids
[i
],
102 length
+ 1, NULL
, name
);
103 glGetPerfMonitorCounterInfoAMD(group
->id
, counterids
[i
],
105 &group
->counters
[i
].type
);
112 get_perfmon_info(struct perfmon_info
*info
)
117 glGetPerfMonitorGroupsAMD(&info
->num_groups
, 0, NULL
);
118 info
->groups
= calloc(info
->num_groups
, sizeof(*info
->groups
));
119 groupids
= calloc(info
->num_groups
, sizeof(*groupids
));
121 glGetPerfMonitorGroupsAMD(NULL
, info
->num_groups
, groupids
);
123 for (i
= 0; i
< info
->num_groups
; i
++) {
124 info
->groups
[i
].id
= groupids
[i
];
125 get_group_info(&info
->groups
[i
]);
132 find_perfcounter(const struct perfmon_info
*info
, const char *group_name
,
133 const char *counter_name
, struct perfcounter_id
*id
)
137 for (i
= 0; i
< info
->num_groups
; i
++) {
138 struct perfmon_group
*group
= &info
->groups
[i
];
140 if (strcmp(group
->name
, group_name
))
143 for (j
= 0; j
< group
->num_counters
; j
++) {
144 struct perfmon_counter
*counter
= &group
->counters
[j
];
146 if (strcmp(counter
->name
, counter_name
))
158 /******************************************************************************/
172 struct perfmon_test
{
176 void (*job
)(const struct perfmon_test
*test
);
177 bool (*check_res
)(uint64_t res
);
181 do_perfmon_test(const struct perfmon_info
*info
,
182 const struct perfmon_test
*test
)
184 struct perfcounter_id counterid
;
185 unsigned perfmon
, counter
;
186 struct counter_res res
= { };
190 if (!find_perfcounter(info
, test
->group
, test
->counter
,
192 piglit_report_subtest_result(PIGLIT_SKIP
, "%s", test
->name
);
196 glGenPerfMonitorsAMD(1, &perfmon
);
197 verify(piglit_check_gl_error(GL_NO_ERROR
));
199 counter
= counterid
.counterid
;
200 glSelectPerfMonitorCountersAMD(perfmon
, true, counterid
.groupid
, 1,
203 /* Start monitoring. */
204 glBeginPerfMonitorAMD(perfmon
);
205 verify(piglit_check_gl_error(GL_NO_ERROR
));
209 /* Stop monitoring. */
210 glEndPerfMonitorAMD(perfmon
);
211 verify(piglit_check_gl_error(GL_NO_ERROR
));
214 glGetPerfMonitorCounterDataAMD(perfmon
,
215 GL_PERFMON_RESULT_AVAILABLE_AMD
,
216 sizeof(avail
), &avail
,
218 verify(piglit_check_gl_error(GL_NO_ERROR
));
219 verify(written
== sizeof(avail
));
222 glGetPerfMonitorCounterDataAMD(perfmon
, GL_PERFMON_RESULT_AMD
,
223 sizeof(res
), (GLuint
*)&res
,
225 verify(piglit_check_gl_error(GL_NO_ERROR
));
226 verify(written
== sizeof(res
));
227 verify(res
.group
== 0 && res
.counter
== counter
);
228 verify(test
->check_res(res
.val
));
230 piglit_report_subtest_result(PIGLIT_PASS
, "%s", test
->name
);
233 #define FEP_VALID_QUADS_REF_VAL 6440
235 static void draw_rect(const struct perfmon_test
*test
)
237 piglit_draw_rect(-1, -1, 3, 3);
240 static void draw_tex(const struct perfmon_test
*test
)
244 tex
= piglit_rgbw_texture(GL_RGBA
, 64, 64, false, true,
246 verify(piglit_check_gl_error(GL_NO_ERROR
));
248 glEnable(GL_TEXTURE_2D
);
249 glBindTexture(GL_TEXTURE_2D
, tex
);
250 piglit_draw_rect_tex(-1, -1, 2, 2, 0, 0, 1, 1);
251 glDisable(GL_TEXTURE_2D
);
252 glDeleteTextures(1, &tex
);
255 static bool fep_valid_quads_check_res(uint64_t res
)
257 return res
== FEP_VALID_QUADS_REF_VAL
;
260 static bool is_zero(uint64_t res
)
265 static bool not_zero(uint64_t res
)
270 static const struct perfmon_test tests
[] = {
272 .name
= "fep-valid-quads",
273 .group
= "V3D counters",
274 .counter
= "FEP-valid-quads",
276 .check_res
= fep_valid_quads_check_res
,
279 .name
= "no-tex-qpu-wait-tmu-zero",
280 .group
= "V3D counters",
281 .counter
= "QPU-total-clk-cycles-waiting-TMU",
283 .check_res
= is_zero
,
286 .name
= "tex-qpu-wait-tmu-not-zero",
287 .group
= "V3D counters",
288 .counter
= "QPU-total-clk-cycles-waiting-TMU",
290 .check_res
= not_zero
,
295 * The main test program.
298 piglit_init(int argc
, char **argv
)
300 struct perfmon_info info
;
303 piglit_require_extension("GL_AMD_performance_monitor");
305 get_perfmon_info(&info
);
307 for (i
= 0; i
< ARRAY_SIZE(tests
); i
++)
308 do_perfmon_test(&info
, &tests
[i
]);