我已经看到了对此问题的其他引用,例如here和here,尽管这些引用了不同版本的Netty。尝试使用4.0分支(4.0.29)和5.0 alpha分支(5.0-Alpha3)中的最新版本。本地(非linux)jdk 1.8.040,很好。远程(Linux)与java jdk 1.8.025-b17得到100%的CPU。 Linux内核版本2.6.32。
尝试使用EpollEventLoopGroup();
尝试调用
workerGroup = new NioEventLoopGroup();
workerGroup.rebuildSelectors();
任何人都可以提供任何建议吗?我已经看到了这个错误与不同版本的Netty的引用。 Jdk bug? Netty bug?进程在启动时立即达到100%并保持在那里。
更新:升级到java 1.8.045,差异相同。
所有可运行线程的JStack output(其中有一些rabbitmq内容,仅包括完整性 - 这对其他应用程序来说是常见的,并不是导致问题的原因)。 / p>
答案 0 :(得分:10)
正如我们在评论中指出的那样,消耗CPU的线程在以下堆栈中忙碌:
"pool-9-thread-1" #49 prio=5 os_prio=0 tid=0x00007ffd508e8000 nid=0x3a0c runnable [0x00007ffd188b6000]
java.lang.Thread.State: RUNNABLE
at java.util.concurrent.ScheduledThreadPoolExecutor$DelayedWorkQueue.poll(ScheduledThreadPoolExecutor.java:809)
at java.util.concurrent.ThreadPoolExecutor.getTask(ThreadPoolExecutor.java:1066)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1127)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
at java.lang.Thread.run(Thread.java:745)
我设法通过创建ScheduledThreadPoolExecutor
来重现类似的行为,将其配置为允许核心线程超时,并通过短暂的延迟安排许多重复任务。它在我的机器上产生大量CPU,jstack
输出相似(有时更深入poll
方法)。此代码重现了它:
ScheduledThreadPoolExecutor executor = new ScheduledThreadPoolExecutor(1);
executor.setKeepAliveTime(1, TimeUnit.MINUTES);
executor.allowCoreThreadTimeOut(true);
for (long i = 0; i < 1000; i++) {
executor.scheduleAtFixedRate(new Runnable() {
@Override
public void run() {
}
}, 0, 1, TimeUnit.NANOSECONDS);
}
现在我们只需确定哪些代码设置了损坏的ScheduledThreadPoolExecutor
。我搜索了RabbitMQ和Netty源代码而没有找到任何obvoius。这可能是你在自己的代码中做的事情吗?
编辑:正如评论中所提到的,根本原因是使用ScheduledThreadPoolExecutor
初始化0
,这显然会导致CPU在某些平台上出现问题。这是在OP的代码中完成的。