0

对于我们开发网络压力测试工具的项目,我们将数据包泛洪到整个子网。我们有一个 Runnable 类,它接受一个端口和广播地址,并在 while(!Thread.currentThread().isInterrupted) 循环中发送一个特定的数据包。然后我们有一个主类,它遍历每个网络接口和每个可能的端口,并将 Runnable 类添加到具有 1000 个线程固定池的 ExecutorService 中。问题是,如果 ExecutorService 等待当前 1000 个线程完成处理,它们永远不会因为它们处于 while 循环中。但是,启动每个线程(65536 * 接口数)会占用太多内存。我们正在寻找一种循环遍历线程的方法,以便它们都有机会运行一段时间并节省内存,同时仍然保持高网络输出。

4

2 回答 2

0

我认为您可能会误以为更多线程总是提供更高的吞吐量。通常情况并非如此。

您的应用程序可能会受 CPU 限制,或受网卡吞吐量的限制。强迫操作系统处理数以万计的线程竞争这些资源不会增加你的吞吐量。只有当线程大部分时间都在等待一些高容量的外部资源(例如数据库)时,大量线程才有帮助。由于您只是在发送数据包并且(可能)对任何响应都不感兴趣,因此没有自然的等待点。

我建议您只拥有与处理器和/或网卡一样多的线程(以较小者为准)。

于 2013-03-27T20:47:43.440 回答
0

与其让每个线程始终运行完成或“永远”运行,不如让线程执行一小部分定义明确的工作,然后将它们重新添加到执行程序。这种高级管理可以通过“控制器”样式的对象来完成,该对象管理将任务重新添加到执行程序队列中,并执行一系列新的步骤。

例如,如果每个任务有 1000 个步骤要重复执行: - 任务 1 运行步骤 1-100,然后通过将自身添加回执行程序队列中的步骤 101-200 来完成 - 任务 2 有机会以类似方式执行(并完成) - 任务 1 现在是队列中的下一个,因此它执行 101-200,然后添加回 201-300 的执行程序队列。- 以此类推,直到任务 1 结束 - 901-1000 - 然后如果它想继续执行,则再次返回 1-100。

在您的情况下,不同的步骤可能是端口,不同的线程代表不同的广播地址 - 按照您认为合适的方式将其分解。

于 2013-03-27T20:53:34.420 回答