Age | Commit message (Collapse) | Author | Files | Lines |
|
The tool trafgen is used in a pktgen style transmit only scenario.
We discovered a performance bottleneck in the kernel, when
running trafgen, where the kernel stalled on a lock in
packet_rcv(). This call is unnecessary for trafgen given its
transmit only nature.
This packet_rcv() call can, easily be avoided by instructing the
RAW/PF_PACKET socket, to not listen to any protocols (by passing
protocol argument zero, when creating the socket).
The performance gain is huge, increasing performance from approx
max 2Mpps to 12Mpps, basically causing trafgen to scale with
the number of CPUs.
Following tests were run on a 2xCPU E5-2650 with Intel 10Gbit/s ixgbe:
Trafgen using sendto() syscall via parameter -t0:
* # CPUs -- *with* -- *without* packet_rcv() call
* 1 CPU == 1,232,244 -- 1,236,144 pkts/sec
* 2 CPUs == 1,592,720 -- 2,593,620 pkts/sec
* 3 CPUs == 1,635,623 -- 3,692,216 pkts/sec
* 4 CPUs == 1,567,768 -- 4,102,866 pkts/sec
* 5 CPUs == 1,700,270 -- 5,151,489 pkts/sec
* 6 CPUs == 1,762,392 -- 6,124,512 pkts/sec
* 7 CPUs == 1,850,139 -- 7,120,496 pkts/sec
* 8 CPUs == 1,770,909 -- 8,058,710 pkts/sec
* 9 CPUs == 1,721,072 -- 8,963,192 pkts/sec
* 10 CPUs == 1,359,157 -- 9,584,535 pkts/sec
* 11 CPUs == 1,175,520 -- 10,498,038 pkts/sec
* 12 CPUs == 1,075,867 -- 11,189,292 pkts/sec
* 13 CPUs == 1,012,602 -- 12,048,836 pkts/sec
* [...]
* 20 CPUs == 1,030,446 -- 11,202,449 pkts/sec
Trafgen using mmap() TX tpacket_v2 (default)
* # CPUs -- *with* -- *without* packet_rcv() call
* 1 CPU == 920,682 -- 927,984 pkts/sec
* 2 CPUs == 1,607,940 -- 2,061,406 pkts/sec
* 3 CPUs == 1,668,488 -- 2,979,463 pkts/sec
* 4 CPUs == 1,423,066 -- 3,169,565 pkts/sec
* 5 CPUs == 1,507,708 -- 3,910,756 pkts/sec
* 6 CPUs == 1,555,616 -- 4,625,844 pkts/sec
* 7 CPUs == 1,560,961 -- 5,298,441 pkts/sec
* 8 CPUs == 1,596,092 -- 6,000,465 pkts/sec
* 9 CPUs == 1,575,139 -- 6,722,130 pkts/sec
* 10 CPUs == 1,311,676 -- 7,114,202 pkts/sec
* 11 CPUs == 1,157,650 -- 7,859,399 pkts/sec
* 12 CPUs == 1,060,366 -- 8,491,004 pkts/sec
* 13 CPUs == 1,012,956 -- 9,269,761 pkts/sec
* [...]
* 20 CPUs == 955,716 -- 8,653,947 pkts/sec
It is fairly strange that the mmap() version runs slower than the
sendto() version. This is likely another performance problem related
to mmap() which seems worth fixing.
Note, that the mmap() version speed can be improved by reducing the
default --ring-size to around 1-2 MiB. But this does not fix general
trend with mmap() performance.
Signed-off-by: Jesper Dangaard Brouer <brouer@redhat.com>
|
|
Also make these options available to trafgen.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
If we loose carrier, don't bother about panic'ing, but continue sending!
Only exit in case we're doing a smoke test.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
Add ability to set IGP in time units in seconds, milliseconds,
microseconds, and nanoseconds by appending a postfix to --gap e.g. --gap
100ms. Also, update the man page and trafgen.zsh to reflect the
changes.
[Fix whitespaces, coding style and minor wording changes -- tklauser]
Signed-off-by: Jon Schipp <jonschipp@gmail.com>
Signed-off-by: Tobias Klauser <tklauser@distanz.ch>
|
|
Get rid of inner loop in fast path. This simplifies code and readability.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
Combine multiple likely conditions into one.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
Fix the following compiler warnings that occur when building with "-W
-Wall -Wextra":
trafgen.c: In function ‘timer_elapsed’:
trafgen.c:136:31: warning: unused parameter ‘number’ [-Wunused-parameter]
trafgen.c: In function ‘apply_csum16’:
trafgen.c:346:36: warning: comparison between signed and unsigned integer expressions [-Wsign-compare]
trafgen.c: In function ‘dump_trafgen_snippet’:
trafgen.c:415:16: warning: comparison between signed and unsigned integer expressions [-Wsign-compare]
trafgen.c: In function ‘xmit_smoke_probe’:
trafgen.c:490:31: warning: comparison between signed and unsigned integer expressions [-Wsign-compare]
trafgen.c:506:32: warning: comparison between signed and unsigned integer expressions [-Wsign-compare]
trafgen.c:509:56: warning: comparison between signed and unsigned integer expressions [-Wsign-compare]
trafgen.c:512:18: warning: comparison between signed and unsigned integer expressions [-Wsign-compare]
trafgen.c: In function ‘__wait_and_sum_others’:
trafgen.c:721:30: warning: comparison between signed and unsigned integer expressions [-Wsign-compare]
trafgen.c: In function ‘__correct_global_delta’:
trafgen.c:743:34: warning: comparison between signed and unsigned integer expressions [-Wsign-compare]
trafgen.c:761:30: warning: comparison between signed and unsigned integer expressions [-Wsign-compare]
trafgen.c: In function ‘xmit_packet_precheck’:
trafgen.c:797:16: warning: comparison between signed and unsigned integer expressions [-Wsign-compare]
trafgen.c:816:47: warning: comparison between signed and unsigned integer expressions [-Wsign-compare]
trafgen.c: In function ‘main_loop’:
trafgen.c:837:17: warning: comparison between signed and unsigned integer expressions [-Wsign-compare]
trafgen.c: In function ‘main’:
trafgen.c:1047:16: warning: comparison between signed and unsigned integer expressions [-Wsign-compare]
trafgen.c:1065:16: warning: comparison between signed and unsigned integer expressions [-Wsign-compare]
trafgen.c:1078:43: warning: comparison between signed and unsigned integer expressions [-Wsign-compare]
trafgen.c:1090:28: warning: comparison between signed and unsigned integer expressions [-Wsign-compare]
Signed-off-by: Tobias Klauser <tklauser@distanz.ch>
|
|
Compiling with "-W -Wall -Wextra" reveals the following warnings in
mac80211.c:
mac80211.c: In function ‘nl80211_init’:
mac80211.c:78:67: warning: unused parameter ‘device’ [-Wunused-parameter]
mac80211.c: In function ‘nl80211_wait_handler’:
mac80211.c:106:48: warning: unused parameter ‘msg’ [-Wunused-parameter]
mac80211.c: In function ‘nl80211_error_handler’:
mac80211.c:115:54: warning: unused parameter ‘nla’ [-Wunused-parameter]
mac80211.c:117:12: warning: unused parameter ‘arg’ [-Wunused-parameter]
mac80211.c: In function ‘nl80211_del_mon_if’:
mac80211.c:181:72: warning: unused parameter ‘device’ [-Wunused-parameter]
Fix them by either marking them as unused (where we need to conform to
library APIs or remove them alltogether (for our own APIs). For the
function leave_rfmon_mac80211() the according users (netsniff-ng and
trafgen) are also changed.
Signed-off-by: Tobias Klauser <tklauser@distanz.ch>
|
|
The variable `i' in apply_counter(), apply_randomizer() and
apply_csum16() is only set once, so use the original parameter
`counter_id' instead. Rename `counter_id' to `id' in order to keep it
short.
Signed-off-by: Tobias Klauser <tklauser@distanz.ch>
|
|
For systems with >8 CPUs it might be i) annoying or ii) uninteresting
to print CPU time statistics. So introduce a switch that can skip this
at exit.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
Those are the last occurences of warnings like:
netsniff-ng.c:697:48: warning: Using plain integer as NULL pointer
netsniff-ng.c:726:48: warning: Using plain integer as NULL pointer
...
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
Commit bf9232fb6 ("trafgen: setup_shared_var: fix couple of things")
forgot to amend the remaining changes in 'len' usage. So lets fix
them right now.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
sparse reported that the variable seed can be made static:
trafgen.c:110:14: warning: symbol 'seed' was not declared. Should it be static?
While at it, also rename a local variable 'seed' to not overlap
contexts.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
1) Fix a couple of sparse warnings:
trafgen.c:382:27: error: cannot size expression
trafgen.c:391:33: error: cannot size expression
trafgen.c:393:33: error: cannot size expression
trafgen.c:401:25: error: cannot size expression
2) Use MAP_FAILED instead of (void *) -1
3) No need to cast to void * on mmap(2)
4) Use NULL instead of 0 as mmap(2)'s first argument
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
In order to be able to better track regressions or to give support,
let us track the Git id as well in version information. This makes
the ``--version'' switch actually useful.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
Took quite a while to git bisect the cause for the wrong TCP checksum
in the -e example. It turned out that commit bf43e1993c7037 ("trafgen:
lexer: return original string if no shellcode") "broke" it, since
before that commit the TCP checksum from -e example was correct and
afterwards not anymore. Well, it didn't break it. What was happening
here is that with this fix above, the packet got 1 byte longer since
the first character of the example string is not omitted anymore,
therefore the checksum got wrong. Fix this by fixing the IP total
length of the packet in the -e and man page example. The UDP example
from the man page still works well if csumudp() is used, so not
affected of this.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
It seems not critical at this point, but lets check it for all offsets
here as well, and mark this check as unlikely to happen.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
In the current situation, it can happen when we set -n1, that no packet
at all will be scheduled. This is due to the case that nearbyint() will
for e.g. 2 cpus round to 0 each, and since in __correct_global_delta()
we only correct a total delta when a particular CPU is allowed to tx
packets (means already has a num > 0), then we correct the delta on the
first such CPU. Switch to using round(), so that on 0.5 it will be round
to the next higher int, and fix the check to >= 0 in __correct_global_delta()
so that a CPU could also get a 0 share of packets. I did a couple of tests
with different -n params and cpu(..) configs and this seems to fix that.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
Finally eliminate xutils.{c,h} and move the rest to epoll2.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
Add an extra file for signal handling functions.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
Remove them from xutils, and add them to socket management.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
Move them out of xutils, so that we can maintain them separately.
Also simplify things a bit.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
Again, also to be able to maintain this more easily.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
Rename xio to ioops (io-ops) and boil its include files down to a
minimum.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
Break this out so that we only need to have sigint non-static where
it is really needed.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
Break out all string handling functions and lockme stuff in order
to further eliminate the big code blob in xutils, so that it can
be easier maintained.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
Break out IRQ functionality from xutils, simplify it, and
save + restore IRQ affinity list.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
Prepare TPACKET_V3 for allowing to transparently setting up the
frame structure such that we do not need to change much in the
netsniff-ng/trafgen code.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
Include long version string into tools when called with --version.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
The entire packet is zeroed using memset() three lines above, thus there
is no need to set icmp->code and icmp->checksum to 0 explicitely again.
Signed-off-by: Tobias Klauser <tklauser@distanz.ch>
|
|
The version() function was missed in the previous commit 785fe152
("trafgen: Add __noreturn attribute to exiting functions"), so add
__noreturn to it now.
Signed-off-by: Tobias Klauser <tklauser@distanz.ch>
|
|
Add the __noreturn attribute to all functions which wont return
but call die() themselves to exit().
Signed-off-by: Tobias Klauser <tklauser@distanz.ch>
|
|
Replace "on default" by "by default", make it a bit more clear what the
seed in the -E/--seed option is for and mention exit after display of
information on --version and --help.
Signed-off-by: Tobias Klauser <tklauser@distanz.ch>
|
|
E.g. when executing trafgen on tap devices, trafgen will complain
that it is not up and running although it was brought up. Remove
this usability restriction and let the kernel decide if it may
send the packets or not.
Reported-by: Aimal Khan <aimal.khan98@gmail.com>
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
If we unmap TX ring buffers and still have timer shots that trigger
the kernel to traverse the TX_RING, it can send out random crap in
some situations. Prevent this by destroying the timer and flush the
TX_RING first in wait mode.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
After commit f9591eebe40c (trafgen: lexer/parser: fix cpu() selection
and whitespacing), we also need to fixup the help description, so that
users start using the cpu(X-Y) notation instead. Also, reintroduce the
alias csum16 for csumip.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
When having a config like cpu(1): {...}, and one runs it with -n1, trafgen
behaves buggy, I also noted that in other situations. Fix this by letting
the loop also return on CPU state RES, and do not perform this stupid magic
in the main routine. So far it seems to work now after some basic tests I
did.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
Let us check the return value when the timer triggers a TX flush
request to the kernel. However, ignore the case of BADFS and NOBUFS.
The socket could already have been closed before the timer triggers
in the first case, and in the second, we just let the next timer
continue processing if currently the buffer space is exhausted.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
|
|
We decided to get rid of the old Git history and start a new one for
several reasons:
*) Allow / enforce only high-quality commits (which was not the case
for many commits in the history), have a policy that is more close
to the one from the Linux kernel. With high quality commits, we
mean code that is logically split into commits and commit messages
that are signed-off and have a proper subject and message body.
We do not allow automatic Github merges anymore, since they are
total bullshit. However, we will either cherry-pick your patches
or pull them manually.
*) The old archive was about ~27MB for no particular good reason.
This basically derived from the bad decision that also some PDF
files where stored there. From this moment onwards, no binary
objects are allowed to be stored in this repository anymore.
The old archive is not wiped away from the Internet. You will still
be able to find it, e.g. on git.cryptoism.org etc.
Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
Signed-off-by: Tobias Klauser <tklauser@distanz.ch>
|