source: test/test-tracetime-parallel.c @ 8decff7

4.0.1-hotfixescachetimestampsdevelopdpdk-ndagetsilivelibtrace4ndag_formatpfringrc-4.0.1rc-4.0.2rc-4.0.3rc-4.0.4ringdecrementfixringperformanceringtimestampfixes
Last change on this file since 8decff7 was 8decff7, checked in by Shane Alcock <salcock@…>, 5 years ago

Update all parallel tests so they compile and run

  • Property mode set to 100644
File size: 7.4 KB
Line 
1/*
2 * This file is part of libtrace
3 *
4 * Copyright (c) 2007 The University of Waikato, Hamilton, New Zealand.
5 * Authors: Richard Sanger
6 *
7 * All rights reserved.
8 *
9 * This code has been developed by the University of Waikato WAND
10 * research group. For further information please see http://www.wand.net.nz/
11 *
12 * libtrace is free software; you can redistribute it and/or modify
13 * it under the terms of the GNU General Public License as published by
14 * the Free Software Foundation; either version 2 of the License, or
15 * (at your option) any later version.
16 *
17 * libtrace is distributed in the hope that it will be useful,
18 * but WITHOUT ANY WARRANTY; without even the implied warranty of
19 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
20 * GNU General Public License for more details.
21 *
22 * You should have received a copy of the GNU General Public License
23 * along with libtrace; if not, write to the Free Software
24 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
25 *
26 * $Id$
27 *
28 */
29
30#ifndef WIN32
31#include <sys/time.h>
32#endif
33#include <stdio.h>
34#include <stdlib.h>
35#include <assert.h>
36#include <sys/types.h>
37#include <signal.h>
38#include <unistd.h>
39#include "libtrace_parallel.h"
40
41static double timeval_to_seconds(struct timeval tv) {
42        return (double) tv.tv_sec + (double) tv.tv_usec / 1000000.0;
43}
44
45static void iferr(libtrace_t *trace,const char *msg)
46{
47        libtrace_err_t err = trace_get_err(trace);
48        if (err.err_num==0)
49                return;
50        printf("Error: %s: %s\n", msg, err.problem);
51        exit(1);
52}
53
54static bool check_range_jitter(double test, double target, double jit) {
55        if ((test <= target + jit) && (test >= target - jit)) {
56                return true;
57        } else {
58                printf("Have:%f Expected:%f (%f-%f)", test, target, target - jit, target + jit);
59                return false;
60        }
61}
62
63
64libtrace_t *trace = NULL;
65int total = 0;
66
67static void signal_handler(int signal)
68{
69        if (signal == SIGALRM) {
70                trace_ppause(trace);
71
72                /* check within 10 seconds we got 9-11 packets */
73                assert(check_range_jitter(10.0, (double) total, 1.0));
74
75                /* Now fullspeed it */
76                trace_set_tracetime(trace, false);
77
78                /* And restart */
79                trace_pstart(trace, NULL, NULL, NULL);
80        }
81}
82
83struct counter {
84        int total;
85        int skipped;
86};
87
88static void *start_report(libtrace_t *trace UNUSED,
89                libtrace_thread_t *t UNUSED, void *global UNUSED) {
90       
91        struct counter *c = (struct counter *)malloc(sizeof(struct counter));
92        c->total = 0;
93        c->skipped = 0;
94        return c;
95
96}
97
98static void stop_report(libtrace_t *trace UNUSED,
99                libtrace_thread_t *t UNUSED, void *global UNUSED, void *tls) {
100
101        struct counter *c = (struct counter *)tls;
102
103        assert(c->skipped <= 20);
104        assert(c->skipped + c->total == 100);
105
106        free(c);
107}
108
109static void report_cb(libtrace_t *trace UNUSED,
110                libtrace_thread_t *sender UNUSED, void *global UNUSED,
111                void *tls, libtrace_result_t *result) {
112
113        struct counter *c = (struct counter *)tls;
114        if (result->type == RESULT_USER)
115                c->total ++;
116        if (result->type == RESULT_USER + 1)
117                c->skipped ++;
118
119        total = c->total;
120
121}
122
123static void *start_process(libtrace_t *trace UNUSED,
124                libtrace_thread_t *t UNUSED, void *global UNUSED) {
125
126        bool *accepting = (bool *)malloc(sizeof(bool));
127        *accepting = true;
128        return accepting;
129
130}
131
132static void stop_process(libtrace_t *trace UNUSED,
133                libtrace_thread_t *t UNUSED, void *global UNUSED, void *tls) {
134        bool *accepting = (bool *)tls;
135        free(accepting);
136}
137
138static void pause_process(libtrace_t *trace UNUSED,
139                libtrace_thread_t *t UNUSED, void *global UNUSED, void *tls) {
140        bool *accepting = (bool *)tls;
141        *accepting = false;
142}
143
144static void resume_process(libtrace_t *trace UNUSED,
145                libtrace_thread_t *t UNUSED, void *global UNUSED, void *tls) {
146        bool *accepting = (bool *)tls;
147        *accepting = true;
148}
149
150static void user_message(libtrace_t *trace UNUSED,
151                libtrace_thread_t *t UNUSED, void *global UNUSED,
152                void *tls UNUSED, int msg UNUSED, libtrace_generic_t ts) {
153
154        struct timeval tv;
155        double time;
156
157        gettimeofday(&tv, NULL);
158        time = timeval_to_seconds(tv);
159
160        assert(check_range_jitter(ts.rdouble, time, 0.01));
161}
162
163static libtrace_packet_t *per_packet(libtrace_t *trace, libtrace_thread_t *t,
164                void *global UNUSED, void *tls, libtrace_packet_t *packet) {
165
166        struct timeval tv;
167        double time;
168        libtrace_message_t message;
169        bool *accepting = (bool *)tls;
170
171        gettimeofday(&tv, NULL);
172        time = timeval_to_seconds(tv);
173
174        if (*accepting) {
175                fprintf(stderr, ".");
176                trace_publish_result(trace, t, (uint64_t)time,
177                                (libtrace_generic_t){.rdouble = time},
178                                RESULT_USER);
179                /* Test that we are not interfering with message delivery */
180                message.code = MESSAGE_USER;
181                message.sender = t;
182                message.data.rdouble = time;
183                trace_message_perpkts(trace, &message);
184        } else {
185                trace_publish_result(trace, t, (uint64_t)time,
186                                (libtrace_generic_t){.rdouble = time},
187                                RESULT_USER+1);
188
189        }
190        return packet;
191
192}
193/**
194 * Test that tracetime playback functions.
195 * Including:
196 * * Delaying packets
197 * * Not blocking messages
198 * * Instantly returning when paused (or stopped)
199 * * Can be switched off/on from a paused state
200 */
201int test_tracetime(const char *tracename) {
202        int error = 0;
203        struct timeval tv;
204        double start, end;
205        libtrace_callback_set_t *processing;
206        libtrace_callback_set_t *reporter;
207
208        gettimeofday(&tv, NULL);
209        start = timeval_to_seconds(tv);
210        printf("Testing delay\n");
211
212        // Create the trace
213        trace = trace_create(tracename);
214        iferr(trace,tracename);
215
216        // Always use 2 threads for simplicity
217        trace_set_perpkt_threads(trace, 2);
218        trace_set_tracetime(trace, true);
219
220        processing = trace_create_callback_set();
221        trace_set_starting_cb(processing, start_process);
222        trace_set_stopping_cb(processing, stop_process);
223        trace_set_pausing_cb(processing, pause_process);
224        trace_set_resuming_cb(processing, resume_process);
225        trace_set_packet_cb(processing, per_packet);
226        trace_set_user_message_cb(processing, user_message);
227
228        reporter = trace_create_callback_set();
229        trace_set_starting_cb(reporter, start_report);
230        trace_set_stopping_cb(reporter, stop_report);
231        trace_set_result_cb(reporter, report_cb);
232
233        trace_set_reporter_thold(trace, 1);
234
235        // Start it
236        trace_pstart(trace, NULL, processing, reporter);
237        iferr(trace,tracename);
238        fprintf(stderr, "Running in tracetime (Will take about 10 seconds)\t");
239
240        // Timeout after 10 which should be about 10 packets seconds
241        alarm(10);
242
243        /* Wait for all threads to stop */
244        trace_join(trace);
245
246        if (error != 0) {
247                iferr(trace,tracename);
248        }
249        /* The whole test should take about 10 seconds */
250        gettimeofday(&tv, NULL);
251        end = timeval_to_seconds(tv);
252        assert(check_range_jitter(end-start, 10.0, 1.0));
253        trace_destroy(trace);
254        return error;
255}
256
257int main() {
258        int error = 0;
259        const char *tracename;
260
261        signal(SIGALRM, signal_handler);
262
263        tracename = "pcapfile:traces/100_seconds.pcap";
264
265        error = test_tracetime(tracename);
266        fprintf(stderr, "\n");
267        return error;
268}
Note: See TracBrowser for help on using the repository browser.