Skip to content

Commit

Permalink
Merge pull request #505 from appneta/Bug_#418_second_packet_timing
Browse files Browse the repository at this point in the history
Bug #418 don't ignore 2nd packet timing
  • Loading branch information
fklassen authored Oct 22, 2018
2 parents 96f588c + 2a2cde5 commit a5f7532
Show file tree
Hide file tree
Showing 3 changed files with 43 additions and 46 deletions.
1 change: 1 addition & 0 deletions docs/CHANGELOG
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
- Out-of-tree build (#482)
- Fails to open tap0 on Zephyr (#411)
- CVE-2018-13112 heap-buffer-overflow in get_l2len (#477 dup #408)
- Respect 2nd packet timing (#418)
- manpage typos (#413)
- Fix replay when using --with-testnic (#178)

Expand Down
77 changes: 41 additions & 36 deletions src/send_packets.c
Original file line number Diff line number Diff line change
Expand Up @@ -495,7 +495,16 @@ send_packets(tcpreplay_t *ctx, pcap_t *pcap, int idx)
bool preload = options->file_cache[idx].cached;
bool top_speed = (options->speed.mode == speed_topspeed ||
(options->speed.mode == speed_mbpsrate && options->speed.speed == 0));
bool now_is_now;
bool now_is_now = false;

if (!timerisset(&ctx->stats.start_time)) {
gettimeofday(&ctx->stats.start_time, NULL);
if (ctx->options->stats >= 0) {
char buf[64];
if (format_date_time(&ctx->stats.start_time, buf, sizeof(buf)) > 0)
printf("Test start: %s ...\n", buf);
}
}

ctx->skip_packets = 0;
start_us = TIMEVAL_TO_MICROSEC(&ctx->stats.start_time);
Expand All @@ -512,12 +521,8 @@ send_packets(tcpreplay_t *ctx, pcap_t *pcap, int idx)
prev_packet = NULL;
}

if (!top_speed) {
if (!top_speed)
gettimeofday(&now, NULL);
now_is_now = true;
} else {
now_is_now = false;
}

/* MAIN LOOP
* Keep sending while we have packets or until
Expand Down Expand Up @@ -557,12 +562,6 @@ send_packets(tcpreplay_t *ctx, pcap_t *pcap, int idx)
pktlen = options->use_pkthdr_len ? (COUNTER)pkthdr_ptr->len : (COUNTER)pkthdr_ptr->caplen;
#endif

/* do we need to print the packet via tcpdump? */
#ifdef ENABLE_VERBOSE
if (options->verbose)
tcpdump_print(options->tcpdump, &pkthdr, pktdata);
#endif

if (ctx->options->unique_ip && ctx->unique_iteration &&
ctx->unique_iteration > ctx->last_unique_iteration) {
/* edit packet to ensure every pass has unique IP addresses */
Expand All @@ -578,7 +577,8 @@ send_packets(tcpreplay_t *ctx, pcap_t *pcap, int idx)
if (ctx->first_time) {
/* get time and timestamp of the first packet */
gettimeofday(&now, NULL);
memcpy(&first_pkt_ts, &pkthdr.ts, sizeof(struct timeval));
now_is_now = true;
memcpy(&first_pkt_ts, &pkthdr.ts, sizeof(first_pkt_ts));
}

/*
Expand Down Expand Up @@ -630,8 +630,13 @@ send_packets(tcpreplay_t *ctx, pcap_t *pcap, int idx)
tcpr_sleep(ctx, sp, &ctx->nap, &now, options->accurate);
}

dbgx(2, "Sending packet #" COUNTER_SPEC, packetnum);
#ifdef ENABLE_VERBOSE
/* do we need to print the packet via tcpdump? */
if (options->verbose)
tcpdump_print(options->tcpdump, &pkthdr, pktdata);
#endif

dbgx(2, "Sending packet #" COUNTER_SPEC, packetnum);
/* write packet out on network */
if (sendpacket(sp, pktdata, pktlen, &pkthdr) < (int)pktlen)
warnx("Unable to send packet: %s", sendpacket_geterr(sp));
Expand Down Expand Up @@ -666,7 +671,7 @@ send_packets(tcpreplay_t *ctx, pcap_t *pcap, int idx)
}

#if defined HAVE_NETMAP
if (sp->first_packet) {
if (sp->first_packet || timesisset(&ctx->nap)) {
wake_send_queues(sp, options);
sp->first_packet = false;
}
Expand Down Expand Up @@ -728,7 +733,16 @@ send_dual_packets(tcpreplay_t *ctx, pcap_t *pcap1, int cache_file_idx1, pcap_t *
COUNTER skip_length = 0;
bool top_speed = (options->speed.mode == speed_topspeed ||
(options->speed.mode == speed_mbpsrate && options->speed.speed == 0));
bool now_is_now;
bool now_is_now = false;

if (!timerisset(&ctx->stats.start_time)) {
gettimeofday(&ctx->stats.start_time, NULL);
if (ctx->options->stats >= 0) {
char buf[64];
if (format_date_time(&ctx->stats.start_time, buf, sizeof(buf)) > 0)
printf("Test start: %s ...\n", buf);
}
}

ctx->skip_packets = 0;
start_us = TIMEVAL_TO_MICROSEC(&ctx->stats.start_time);
Expand All @@ -751,12 +765,8 @@ send_dual_packets(tcpreplay_t *ctx, pcap_t *pcap1, int cache_file_idx1, pcap_t *
pktdata1 = get_next_packet(ctx, pcap1, &pkthdr1, cache_file_idx1, prev_packet1);
pktdata2 = get_next_packet(ctx, pcap2, &pkthdr2, cache_file_idx2, prev_packet2);

if (!top_speed) {
if (!top_speed)
gettimeofday(&now, NULL);
now_is_now = true;
} else {
now_is_now = false;
}

/* MAIN LOOP
* Keep sending while we have packets or until
Expand Down Expand Up @@ -823,12 +833,6 @@ send_dual_packets(tcpreplay_t *ctx, pcap_t *pcap1, int cache_file_idx1, pcap_t *
pktlen = options->use_pkthdr_len ? (COUNTER)pkthdr_ptr->len : (COUNTER)pkthdr_ptr->caplen;
#endif

/* do we need to print the packet via tcpdump? */
#ifdef ENABLE_VERBOSE
if (options->verbose)
tcpdump_print(options->tcpdump, pkthdr_ptr, pktdata);
#endif

if (ctx->options->unique_ip && ctx->unique_iteration &&
ctx->unique_iteration > ctx->last_unique_iteration) {
/* edit packet to ensure every pass is unique */
Expand All @@ -843,6 +847,7 @@ send_dual_packets(tcpreplay_t *ctx, pcap_t *pcap1, int cache_file_idx1, pcap_t *
if (ctx->first_time) {
/* get time and timestamp of the first packet */
gettimeofday(&now, NULL);
now_is_now = true;
memcpy(&first_pkt_ts, &pkthdr_ptr->ts, sizeof(struct timeval));
}

Expand Down Expand Up @@ -895,8 +900,13 @@ send_dual_packets(tcpreplay_t *ctx, pcap_t *pcap1, int cache_file_idx1, pcap_t *
tcpr_sleep(ctx, sp, &ctx->nap, &now, options->accurate);
}

dbgx(2, "Sending packet #" COUNTER_SPEC, packetnum);
#ifdef ENABLE_VERBOSE
/* do we need to print the packet via tcpdump? */
if (options->verbose)
tcpdump_print(options->tcpdump, pkthdr_ptr, pktdata);
#endif

dbgx(2, "Sending packet #" COUNTER_SPEC, packetnum);
/* write packet out on network */
if (sendpacket(sp, pktdata, pktlen, pkthdr_ptr) < (int)pktlen)
warnx("Unable to send packet: %s", sendpacket_geterr(sp));
Expand Down Expand Up @@ -927,7 +937,7 @@ send_dual_packets(tcpreplay_t *ctx, pcap_t *pcap1, int cache_file_idx1, pcap_t *
}

#if defined HAVE_NETMAP
if (sp->first_packet) {
if (sp->first_packet || timesisset(&ctx->nap)) {
wake_send_queues(sp, options);
sp->first_packet = false;
}
Expand Down Expand Up @@ -1133,18 +1143,16 @@ static bool calc_sleep_time(tcpreplay_t *ctx, struct timeval *pkt_time_delta,
case speed_multiplier:
/*
* Replay packets a factor of the time they were originally sent.
* Make sure the packet is not late.
*/
if (timerisset(last_delta)) {
/* make sure the packet is not late */
{
COUNTER delta_us, delta_pkt_time;
now_us = TIMSTAMP_TO_MICROSEC(sent_timestamp);
delta_pkt_time = TIMEVAL_TO_MICROSEC(pkt_time_delta);
delta_us = now_us - *start_us;
if (timercmp(pkt_time_delta, last_delta, >) && (delta_pkt_time > delta_us)) {
/* pkt_time_delta has increased, so handle normally */
timersub(pkt_time_delta, last_delta, &nap_for);
dbgx(3, "original packet delta pkt_time: " TIMEVAL_FORMAT, nap_for.tv_sec, nap_for.tv_usec);

TIMEVAL_TO_TIMESPEC(&nap_for, &ctx->nap);
dbgx(3, "original packet delta time: " TIMESPEC_FORMAT, ctx->nap.tv_sec, ctx->nap.tv_nsec);
timesdiv_float(&ctx->nap, options->speed.multiplier);
Expand All @@ -1153,9 +1161,6 @@ static bool calc_sleep_time(tcpreplay_t *ctx, struct timeval *pkt_time_delta,
/* Don't sleep if this packet is late or in the past */
update_time = false;
}
} else {
/* Don't sleep if this is our first packet */
update_time = false;
}
break;

Expand Down
11 changes: 1 addition & 10 deletions src/tcpreplay_api.c
Original file line number Diff line number Diff line change
Expand Up @@ -1102,20 +1102,11 @@ tcpreplay_replay(tcpreplay_t *ctx)
return -1;
}

init_timestamp(&ctx->stats.start_time);
init_timestamp(&ctx->stats.last_time);
init_timestamp(&ctx->stats.last_print);
init_timestamp(&ctx->stats.end_time);

if (gettimeofday(&ctx->stats.start_time, NULL) < 0) {
tcpreplay_seterr(ctx, "gettimeofday() failed: %s", strerror(errno));
return -1;
}

if (ctx->options->stats >= 0) {
if (format_date_time(&ctx->stats.start_time, buf, sizeof(buf)) > 0)
printf("Test start: %s ...\n", buf);
}

ctx->running = true;
total_loops = ctx->options->loop;
loop = 0;
Expand Down

0 comments on commit a5f7532

Please sign in to comment.