【问题标题】:tomcat: Waiting on condition threadtomcat:等待条件线程
【发布时间】:2017-12-25 02:19:08
【问题描述】:

我正在调查tomcat关闭过程的奇怪问题:在runnig shutdown.sh之后java进程仍然出现(我使用ps -ef|grep tomcat检查它) 情况有点复杂,因为我对服务器的访问非常有限(例如没有调试)

我使用远程jConsole 和热点功能进行了线程转储(通过使用kill -3 <PID>)和堆转储。

查看线程转储后,我发现:

"pool-2-thread-1" #74 prio=5 os_prio=0 tid=0x00007f3354359800 nid=0x7b46 waiting on condition [0x00007f333e55d000]
  java.lang.Thread.State: WAITING (parking)
       at sun.misc.Unsafe.park(Native Method)
       - parking to wait for  <0x00000000c378d330> (a java.util.concurrent.locks.AbstractQueuedSynchronizer$ConditionObject)
       at java.util.concurrent.locks.LockSupport.park(LockSupport.java:175)
       at java.util.concurrent.locks.AbstractQueuedSynchronizer$ConditionObject.await(AbstractQueuedSynchronizer.java:2039)
       at java.util.concurrent.ScheduledThreadPoolExecutor$DelayedWorkQueue.take(ScheduledThreadPoolExecutor.java:1081)
       at java.util.concurrent.ScheduledThreadPoolExecutor$DelayedWorkQueue.take(ScheduledThreadPoolExecutor.java:809)
       at java.util.concurrent.ThreadPoolExecutor.getTask(ThreadPoolExecutor.java:1067)
       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:748)

所以,我对问题的理解如下: CachedThreadpool 中使用了一个资源(数据库连接或其他),该资源现在被锁定, 并防止线程pool-2-thread-1 停止。假设这个线程不是守护进程——JVM 不能优雅地停止。

有没有办法找出哪个资源被锁定,从哪里锁定以及如何避免这种情况?另一个问题是——如何预防这种情况? 另一个是:地址 0x00007f333e55d000 是干什么用的?

谢谢!

【问题讨论】:

    标签: java multithreading tomcat threadpool threadpoolexecutor


    【解决方案1】:

    经过一番挣扎后,我发现,冻结线程始终具有相同的名称pool-2-thread-1。我 grep 项目的所有来源以查找启动任何计划线程池的任何位置:Executors#newScheduledThreadPool。经过大量时间后,我用线程池中的线程名称记录了所有这些地方。 再重新启动一个服务器并解决问题!

    我发现了一个线程池,它只用一个线程启动并使用以下代码:

    private void shutdownThreadpool(int tries) {
        try {
            boolean terminated;
            LOGGER.debug("Trying to shutdown thread pool in {} tries", tries);
            pool.shutdown();
            do {
                terminated = pool.awaitTermination(WAIT_ON_SHUTDOWN,TimeUnit.MILLISECONDS);
                if (--tries == 0
                        && !terminated) {
                    LOGGER.debug("After 10 attempts couldn't shutdown thread pool, force shutdown");
                    pool.shutdownNow();
                    terminated = pool.awaitTermination(WAIT_ON_SHUTDOWN, TimeUnit.MILLISECONDS);
                    if (!terminated) {
                        LOGGER.debug("Cannot stop thread pool even with force");
                        LOGGER.trace("Some of the workers doesn't react to Interruption event properly");
                        terminated = true;
                    }
                } else {
                    LOGGER.info("After {} attempts doesn't stop", tries);
                }
            } while (!terminated);
            LOGGER.debug("Successfully stop thread pool");
        } catch (final InterruptedException ie) {
            LOGGER.warn("Thread pool shutdown interrupted");
        }
    }
    

    之后问题就解决了。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2017-07-02
      • 1970-01-01
      • 2012-06-14
      • 1970-01-01
      • 2019-10-31
      • 1970-01-01
      • 1970-01-01
      • 2014-01-31
      相关资源
      最近更新 更多