我有一个不断创建和删除网络命名空间的 linux 应用程序(用 C 编写)。通常一个创建/删除周期大约需要 300 毫秒。
在性能调查期间,我对程序运行了 strace 以找出哪个系统调用花费的时间最多。从 strace 输出来看,似乎第一次调用 unshare 在我的系统上只需要 4 毫秒,但随后的调用需要接近 200 毫秒。
strace -p <pid> -T
unshare(CLONE_NEWNET) = 0 <0.004150>
unshare(CLONE_NEWNET) = 0 <0.192055>
unshare(CLONE_NEWNET) = 0 <0.192872>
unshare(CLONE_NEWNET) = 0 <0.190303>
unshare(CLONE_NEWNET) = 0 <0.193062>
该程序的结构使得在循环(内部控制循环)开始时,它创建一个网络命名空间并在循环结束时删除命名空间。
只是为了试验,我修改了我的应用程序,使其在控制周期结束时不删除网络命名空间——只创建新的网络命名空间,但从不删除它们。这显着提高了性能,并且我在随后的 unshare 系统调用调用中没有任何延迟。每个 unshare 系统调用需要 2-3 毫秒。
strace -p <pid> -T
unshare(CLONE_NEWNET) = 0 <0.003102>
unshare(CLONE_NEWNET) = 0 <0.002980>
unshare(CLONE_NEWNET) = 0 <0.003070>
unshare(CLONE_NEWNET) = 0 <0.003124>
unshare(CLONE_NEWNET) = 0 <0.002952>
显然,删除网络命名空间会以某种方式影响/延迟随后的网络命名空间创建。
这里会发生什么?我该如何进一步调试呢?
我正在使用 linux 内核 3.12.9-301.fc20.x86_64。