]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - contrib/processor-trace/libipt/test/src/ptunit-time.c
Import Intel Processor Trace decoder library from
[FreeBSD/FreeBSD.git] / contrib / processor-trace / libipt / test / src / ptunit-time.c
1 /*
2  * Copyright (c) 2014-2018, Intel Corporation
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions are met:
6  *
7  *  * Redistributions of source code must retain the above copyright notice,
8  *    this list of conditions and the following disclaimer.
9  *  * Redistributions in binary form must reproduce the above copyright notice,
10  *    this list of conditions and the following disclaimer in the documentation
11  *    and/or other materials provided with the distribution.
12  *  * Neither the name of Intel Corporation nor the names of its contributors
13  *    may be used to endorse or promote products derived from this software
14  *    without specific prior written permission.
15  *
16  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
17  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19  * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
20  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
21  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
22  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
23  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
24  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
25  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
26  * POSSIBILITY OF SUCH DAMAGE.
27  */
28
29 #include "pt_time.h"
30
31 #include "intel-pt.h"
32
33 #include "ptunit.h"
34
35
36 /* A time unit test fixture. */
37
38 struct time_fixture {
39         /* The configuration to use. */
40         struct pt_config config;
41
42         /* The calibration to use. */
43         struct pt_time_cal tcal;
44
45         /* The time struct to update. */
46         struct pt_time time;
47
48         /* The test fixture initialization and finalization functions. */
49         struct ptunit_result (*init)(struct time_fixture *);
50         struct ptunit_result (*fini)(struct time_fixture *);
51 };
52
53 static struct ptunit_result tfix_init(struct time_fixture *tfix)
54 {
55         memset(&tfix->config, 0, sizeof(tfix->config));
56         tfix->config.size = sizeof(tfix->config);
57         tfix->config.cpuid_0x15_eax = 2;
58         tfix->config.cpuid_0x15_ebx = 1;
59         tfix->config.mtc_freq = 4;
60
61         pt_tcal_init(&tfix->tcal);
62         pt_tcal_set_fcr(&tfix->tcal, 0x2ull << pt_tcal_fcr_shr);
63
64         pt_time_init(&tfix->time);
65
66         return ptu_passed();
67 }
68
69
70 static struct ptunit_result tsc_null(struct time_fixture *tfix)
71 {
72         struct pt_packet_tsc packet;
73         int errcode;
74
75         errcode = pt_time_update_tsc(NULL, &packet, &tfix->config);
76         ptu_int_eq(errcode, -pte_internal);
77
78         errcode = pt_time_update_tsc(&tfix->time, NULL, &tfix->config);
79         ptu_int_eq(errcode, -pte_internal);
80
81         return ptu_passed();
82 }
83
84 static struct ptunit_result cbr_null(struct time_fixture *tfix)
85 {
86         struct pt_packet_cbr packet;
87         int errcode;
88
89         errcode = pt_time_update_cbr(NULL, &packet, &tfix->config);
90         ptu_int_eq(errcode, -pte_internal);
91
92         errcode = pt_time_update_cbr(&tfix->time, NULL, &tfix->config);
93         ptu_int_eq(errcode, -pte_internal);
94
95         return ptu_passed();
96 }
97
98 static struct ptunit_result tma_null(struct time_fixture *tfix)
99 {
100         struct pt_packet_tma packet;
101         int errcode;
102
103         errcode = pt_time_update_tma(NULL, &packet, &tfix->config);
104         ptu_int_eq(errcode, -pte_internal);
105
106         errcode = pt_time_update_tma(&tfix->time, NULL, &tfix->config);
107         ptu_int_eq(errcode, -pte_internal);
108
109         errcode = pt_time_update_tma(&tfix->time, &packet, NULL);
110         ptu_int_eq(errcode, -pte_internal);
111
112         return ptu_passed();
113 }
114
115 static struct ptunit_result mtc_null(struct time_fixture *tfix)
116 {
117         struct pt_packet_mtc packet;
118         int errcode;
119
120         errcode = pt_time_update_mtc(NULL, &packet, &tfix->config);
121         ptu_int_eq(errcode, -pte_internal);
122
123         errcode = pt_time_update_mtc(&tfix->time, NULL, &tfix->config);
124         ptu_int_eq(errcode, -pte_internal);
125
126         errcode = pt_time_update_mtc(&tfix->time, &packet, NULL);
127         ptu_int_eq(errcode, -pte_internal);
128
129         return ptu_passed();
130 }
131
132 static struct ptunit_result cyc_null(struct time_fixture *tfix)
133 {
134         struct pt_packet_cyc packet;
135         int errcode;
136
137         errcode = pt_time_update_cyc(NULL, &packet, &tfix->config, 0ull);
138         ptu_int_eq(errcode, -pte_internal);
139
140         errcode = pt_time_update_cyc(&tfix->time, NULL, &tfix->config, 0ull);
141         ptu_int_eq(errcode, -pte_internal);
142
143         errcode = pt_time_update_cyc(&tfix->time, &packet, NULL, 0ull);
144         ptu_int_eq(errcode, -pte_internal);
145
146         return ptu_passed();
147 }
148
149 static struct ptunit_result query_tsc_null(struct time_fixture *tfix)
150 {
151         uint64_t tsc;
152         int errcode;
153
154         errcode = pt_time_query_tsc(NULL, NULL, NULL, &tfix->time);
155         ptu_int_eq(errcode, -pte_internal);
156
157         errcode = pt_time_query_tsc(&tsc, NULL, NULL, NULL);
158         ptu_int_eq(errcode, -pte_internal);
159
160         return ptu_passed();
161 }
162
163 static struct ptunit_result query_tsc_none(struct time_fixture *tfix)
164 {
165         uint64_t tsc;
166         int errcode;
167
168         errcode = pt_time_query_tsc(&tsc, NULL, NULL, &tfix->time);
169         ptu_int_eq(errcode, -pte_no_time);
170
171         return ptu_passed();
172 }
173
174 static struct ptunit_result query_cbr_null(struct time_fixture *tfix)
175 {
176         uint32_t cbr;
177         int errcode;
178
179         errcode = pt_time_query_cbr(NULL, &tfix->time);
180         ptu_int_eq(errcode, -pte_internal);
181
182         errcode = pt_time_query_cbr(&cbr, NULL);
183         ptu_int_eq(errcode, -pte_internal);
184
185         return ptu_passed();
186 }
187
188 static struct ptunit_result query_cbr_none(struct time_fixture *tfix)
189 {
190         uint32_t cbr;
191         int errcode;
192
193         errcode = pt_time_query_cbr(&cbr, &tfix->time);
194         ptu_int_eq(errcode, -pte_no_cbr);
195
196         return ptu_passed();
197 }
198
199 static struct ptunit_result tcal_cbr_null(struct time_fixture *tfix)
200 {
201         struct pt_packet_cbr packet;
202         int errcode;
203
204         errcode = pt_tcal_update_cbr(NULL, &packet, &tfix->config);
205         ptu_int_eq(errcode, -pte_internal);
206
207         return ptu_passed();
208 }
209
210 static struct ptunit_result tcal_mtc_null(struct time_fixture *tfix)
211 {
212         struct pt_packet_mtc packet;
213         int errcode;
214
215         errcode = pt_tcal_update_mtc(NULL, &packet, &tfix->config);
216         ptu_int_eq(errcode, -pte_internal);
217
218         errcode = pt_tcal_update_mtc(&tfix->tcal, NULL, &tfix->config);
219         ptu_int_eq(errcode, -pte_internal);
220
221         errcode = pt_tcal_update_mtc(&tfix->tcal, &packet, NULL);
222         ptu_int_eq(errcode, -pte_internal);
223
224         return ptu_passed();
225 }
226
227 static struct ptunit_result tcal_cyc_null(struct time_fixture *tfix)
228 {
229         struct pt_packet_cyc packet;
230         int errcode;
231
232         errcode = pt_tcal_update_cyc(NULL, &packet, &tfix->config);
233         ptu_int_eq(errcode, -pte_internal);
234
235         errcode = pt_tcal_update_cyc(&tfix->tcal, NULL, &tfix->config);
236         ptu_int_eq(errcode, -pte_internal);
237
238         return ptu_passed();
239 }
240
241 static struct ptunit_result tsc(struct time_fixture *tfix)
242 {
243         struct pt_packet_tsc packet;
244         uint64_t tsc;
245         uint32_t lost_mtc, lost_cyc;
246         int errcode;
247
248         packet.tsc = 0xdedededeull;
249
250         errcode = pt_time_update_tsc(&tfix->time, &packet, &tfix->config);
251         ptu_int_eq(errcode, 0);
252
253         errcode = pt_time_query_tsc(&tsc, &lost_mtc, &lost_cyc, &tfix->time);
254         ptu_int_eq(errcode, 0);
255
256         ptu_uint_eq(tsc, 0xdedededeull);
257         ptu_uint_eq(lost_mtc, 0);
258         ptu_uint_eq(lost_cyc, 0);
259
260         return ptu_passed();
261 }
262
263 static struct ptunit_result cbr(struct time_fixture *tfix)
264 {
265         struct pt_packet_cbr packet;
266         uint32_t cbr;
267         int errcode;
268
269         packet.ratio = 0x38;
270
271         errcode = pt_time_update_cbr(&tfix->time, &packet, &tfix->config);
272         ptu_int_eq(errcode, 0);
273
274         errcode = pt_time_query_cbr(&cbr, &tfix->time);
275         ptu_int_eq(errcode, 0);
276
277         ptu_uint_eq(cbr, 0x38);
278
279         return ptu_passed();
280 }
281
282 static struct ptunit_result tma(struct time_fixture *tfix)
283 {
284         struct pt_packet_tma packet;
285         int errcode;
286
287         packet.ctc = 0xdc;
288         packet.fc = 0xf;
289
290         errcode = pt_time_update_tma(&tfix->time, &packet, &tfix->config);
291         ptu_int_eq(errcode, -pte_bad_context);
292
293         return ptu_passed();
294 }
295
296 static struct ptunit_result mtc(struct time_fixture *tfix)
297 {
298         struct pt_packet_mtc packet;
299         uint64_t tsc;
300         int errcode;
301
302         packet.ctc = 0xdc;
303
304         errcode = pt_time_update_mtc(&tfix->time, &packet, &tfix->config);
305         ptu_int_eq(errcode, 0);
306
307         errcode = pt_time_query_tsc(&tsc, NULL, NULL, &tfix->time);
308         ptu_int_eq(errcode, -pte_no_time);
309
310         return ptu_passed();
311 }
312
313 static struct ptunit_result cyc(struct time_fixture *tfix)
314 {
315         struct pt_packet_cyc packet;
316         uint64_t fcr, tsc;
317         int errcode;
318
319         errcode = pt_tcal_fcr(&fcr, &tfix->tcal);
320         ptu_int_eq(errcode, 0);
321
322         packet.value = 0xdc;
323
324         errcode = pt_time_update_cyc(&tfix->time, &packet, &tfix->config, fcr);
325         ptu_int_eq(errcode, 0);
326
327         errcode = pt_time_query_tsc(&tsc, NULL, NULL, &tfix->time);
328         ptu_int_eq(errcode, -pte_no_time);
329
330         return ptu_passed();
331 }
332
333
334 int main(int argc, char **argv)
335 {
336         struct ptunit_suite suite;
337         struct time_fixture tfix;
338
339         suite = ptunit_mk_suite(argc, argv);
340
341         tfix.init = tfix_init;
342         tfix.fini = NULL;
343
344         ptu_run_f(suite, tsc_null, tfix);
345         ptu_run_f(suite, cbr_null, tfix);
346         ptu_run_f(suite, tma_null, tfix);
347         ptu_run_f(suite, mtc_null, tfix);
348         ptu_run_f(suite, cyc_null, tfix);
349
350         ptu_run_f(suite, query_tsc_null, tfix);
351         ptu_run_f(suite, query_tsc_none, tfix);
352         ptu_run_f(suite, query_cbr_null, tfix);
353         ptu_run_f(suite, query_cbr_none, tfix);
354
355         ptu_run_f(suite, tcal_cbr_null, tfix);
356         ptu_run_f(suite, tcal_mtc_null, tfix);
357         ptu_run_f(suite, tcal_cyc_null, tfix);
358
359         ptu_run_f(suite, tsc, tfix);
360         ptu_run_f(suite, cbr, tfix);
361         ptu_run_f(suite, tma, tfix);
362         ptu_run_f(suite, mtc, tfix);
363         ptu_run_f(suite, cyc, tfix);
364
365         /* The bulk is covered in ptt tests. */
366
367         return ptunit_report(&suite);
368 }