如何衡量网络性能(如何对网络协议进行基准测试)

Jak*_*ski 12 benchmarking networking profiling network-programming network-protocols

首先,有点背景.分布式版本控制系统(DVCS)有许多不同的比较,它们比较存储库的大小或基准操作速度.我没有找到任何可以对各种DVCS的网络性能进行基准测试,以及所使用的各种协议......除了测量涉及网络的操作(命令)的速度,如'clone','pull'/'fetch'或'push'.

我想知道你怎么做这样的比较; 如何衡量应用程序的网络性能,或如何测试网络协议.我在这里设想还测量性能对网络带宽和网络延迟(ping时间)的依赖性; 一些协议以更多往返交换(协商)的形式牺牲等待时间以发送最小所需的最终"包".

如果可能的话,我宁愿只涉及一台计算机的解决方案.我想看看开源解决方案,在Linux上工作.但我也欢迎更通用的答案.

首选操作系统: Linux
首选语言: C,Perl,shell脚本


可能的测量:

  • 在一个会话中从服务器传输到客户端以及从客户端传输到服务器的总字节数; 这也可以用来衡量协议的开销(带宽)
  • 一次交易中的往返次数(延迟)
  • 从网络带宽和网络延迟(ping时间)的网络操作速度(克隆/拉/推)所需的时间依赖性

如何进行此类测量(此类基准测试)?


添加02-06-2009:
最简单的基准测试(测量)将是time命令的网络版本,即运行的命令将给出我传输的字节数,以及执行给定命令期间的往返/网络连接数.


添加09-06-2009:上面提到的网络版命令解决方案的虚构输出
示例time如下所示:

$ ntime git clone -q git://git.example.com/repo.git
...
bytes sent: nnn (nn kiB), bytes received: nnn (nn kiB), avg: nn.nn KB/s
nn reads, nn writes
Run Code Online (Sandbox Code Playgroud)

请注意,它只是一个示例输出,详细说明了可能想要获得的信息类型.


添加09-06-2009:
看起来我想要的一些东西可以使用dummynet,工具(最初)来测试网络协议......

non*_*one 15

如果我正确理解你,你基本上对Linux'strace'(简介)这样的网络特定系统调用感兴趣吗?

可能是分析器和调试器的组合,用于网络应用(即'ntrace'),提供各种可选测量的详细分析?

在Linux下,strace实用程序主要基于Linux内核提供的功能,即ptrace(进程跟踪) API:

使用ptrace,应该可以获得您感兴趣的大部分数据.

在Windows上,您可能希望调查弯路以拦截/重定向Winsock API调用以进行检查/基准测试.

如果你真的不需要所有那么多低级别的信息,你也可以直接使用strace(在linux上)并且只用它来跟踪某些系统调用,例如考虑以下行,它只跟踪对open syscall的调用(使用附加的-o FILE参数,可以将所有输出重定向到输出文件):

strace -e trace=open -o results.log

通过将另一个-v标志传递给strace,您可以增加其详细程度以获取其他信息(当使用由许多较小的shell实用程序和独立工具组成的git之类的SCM时,您可能还需要考虑使用 - f标志,以便也遵循分叉进程).

所以,你会感兴趣的是所有与套接字相关的系统调用,即:

  • 接受
  • 捆绑
  • getpeername
  • getsockname
  • 用getsockopt
  • 的recv
  • recvfrom的
  • 发送
  • 发送至
  • setsockopt的
  • 关掉
  • 插座
  • socketpair

(在开始时,你可能只想查看处理send .../recv ...调用)

为简化此操作,您还可以使用"network"作为跟踪参数,这将跟踪所有与网络相关的调用:

-e trace = network:跟踪所有与网络相关的系统调用.

因此,相应的strace调用可能如下所示:

strace -v -e trace=accept,bind,connect,getpeername,getsockname,getsockopt,listen,recv,recvfrom,send,sendto setsockopt,shutdown,socket,socketpair -o results.log -f git pull

程序运行完毕后,您将主要检查日志文件以评估数据,然后可以使用正则表达式轻松实现.

例如,在linux shell中运行以下代码时: strace -v -o wget.log -e trace=connect,recv,recvfrom,send,sendto wget http://www.google.com

生成的日志文件包含以下消息:

  • recv(3,"HTTP/1.0 302 Found\r \n位置:htt"...,511,MSG_PEEK)= 511
  • sendto(4,"\ 24\0\0\0\26\0\1\3 ^\206*J\0\0\0\0\0\0\0\0"......,20,0 ,{sa_family = AF_NETLINK,pid = 0,groups = 00000000},12)= 20

查看这两个系统调用的手册页,很明显511和20分别是传输的字节数.如果您还需要详细的计时信息,可以将-T标志传递给strace:

-T - 在每个系统调用中花费的打印时间

此外,您可以通过传递-c标志来获取一些统计信息:

-c:计算每个系统调用的时间,调用和错误,并报告程序退出的摘要.在Linux上,这会尝试显示系统时间(在内核中运行的CPU时间),与挂钟时间无关.如果-c与-f或-F(下面)一起使用,则仅保留所有跟踪进程的聚合总计.

如果还需要检查处理的实际数据,可能需要查看读/写说明符:

-e read = set:对从指定集中列出的文件描述符读取的所有数据执行完整的十六进制和ASCII转储.例如,要查看文件描述符3和5上的所有输入活动,请使用-e read = 3,5.请注意,这与read(2)系统调用的正常跟踪无关,该调用由选项-e trace = read控制.-e write = set:对写入指定集中列出的文件描述符的所有数据执行完整的十六进制和ASCII转储.例如,要查看文件描述符3和5上的所有输出活动,请使用-e write = 3,5.请注意,这与write(2)系统调用的正常跟踪无关,该调用由选项-e trace = write控制.

您还可以自定义字符串的最大长度:

-s strsize:指定要打印的最大字符串大小(默认值为32).请注意,文件名不被视为字符串,并且始终完整打印

或者将字符串转换为十六进制:

-xx:以十六进制字符串格式打印所有字符串.

因此,在大部分情况下使用strace,似乎是一种很好的混合方法,因为它很容易做到,但仍然有大量的低级信息可用,如果你发现你需要额外的低级别信息,你可能想要考虑扩展strace而不是使用sourceforge上的strace项目归档相应的功能请求.

然而,更多地考虑它,实现一个相当简单的网络流量基准的一个较少涉及和更多平台无关的方式,将在客户端和实际服务器之间使用某种形式的中间层:一个基本上计量的服务器,分析流量并将流量重定向到真实服务器.

非常类似于代理服务器(例如SOCKS),因此所有流量都通过分析器进行隧道传输,而分析器可以累积统计数据和其他指标.

这样的基本版本可能很容易通过使用netcat和一些shell脚本放在一起,但更复杂的版本可能会因使用perl或python而受益.

对于SOCKS服务器的python实现,您可能希望查看pysocks.

此外,当然扭曲 python:

Twisted是一个用Python编写并根据MIT许可证授权的事件驱动的网络引擎.

如果您确实需要更多低级别信息,那么您可能真的想要查看拦截系统调用.

如果您还需要特定于协议的效率数据,则可能需要查看tcpdump.


Jak*_*ski 5

可能的答案是使用SystemTap.在示例脚本中,有nettop以"顶部"的方式显示(某些)所需的网络信息,并且有iotime脚本以所需的形式显示I/O信息.