#java #tomcat #memory-leaks
#java #tomcat #утечки памяти
Вопрос:
РЕДАКТИРОВАТЬ: Тема форума Hibernate по этой проблеме:https://forum.hibernate.org/viewtopic.php?f=1amp;t=1035073
Я использую hibernate-4.3.1
, ehcache-core-2.6.7
c3p0-0.9.5-pre5
наряду с Tomcat 7.0.27
, и я испытываю большую утечку PermGen при отключении приложения.
Я выяснил, что существует множество классов, закрепленных с помощью WebappClassLoader
(вот список, как показывает JProfiler. Первое число — это количество объектов этого класса в памяти)
Вот код в ContextListener.contextDestroyed()
:
@Override
public void contextDestroyed(ServletContextEvent event) {
Debug.log.info("SERVER UNDEPLOY:");
serviceManager.destroyServices();
serviceManager = null; // this is static field :(
for (Object o : C3P0Registry.getPooledDataSources()) {
PooledDataSource dataSource = (PooledDataSource) o;
try {
Debug.log.info(String.format(
"-> deregistering C3P0 pool: size %s",
dataSource.getThreadPoolSize()));
dataSource.close();
Thread.sleep(500);
} catch (SQLException e) {
Debug.log.error(String.format(
" FAILED deregistering C3P0 pool: %s",
dataSource.getDataSourceName()), e);
} catch (InterruptedException e) {
}
}
Debug.log.info("-> shutting down cache manager");
CacheManager.getInstance().shutdown();
Enumeration<Driver> drivers = DriverManager.getDrivers();
while (drivers.hasMoreElements()) {
Driver driver = drivers.nextElement();
try {
Debug.log.info(String.format(
"-> deregistering jdbc driver: %s", driver));
DriverManager.deregisterDriver(driver);
} catch (SQLException e) {
Debug.log.error(String.format(
" FAILED deregistering driver %s", driver), e);
}
}
Debug.log.info("-> shutting down Hibernate factories");
Hibernate.factory.close(); //SessionFactory
Hibernate.factory = null; // static field :(
Debug.log.info("-> stopping logger");
Debug.log.info("............ SERVER stop ...................");
((LoggerContext) LoggerFactory.getILoggerFactory()).stop();
}
Я пытался проанализировать корни объектов GC в профилировщике, но безуспешно. Кто-нибудь может подсказать, почему это может быть?
Комментарии:
1. Вы прошли через
MemoryLeakProtection
Tomcat? Подробнее @ wiki.apache.org/tomcat/MemoryLeakProtection2. ДА. Рассматриваемый код отменяет регистрацию драйвера JDBC, и я уже знаю о статических переменных и о том, как они могут что-то хранить. Мое приложение само не создает потоки и не работает с загрузчиками классов.
Ответ №1:
я рад, что вы закрываете () свои источники данных contextDestroyed(...)
!
Но вы также можете попробовать две новые настройки в c3p0, предназначенные специально для решения проблем с утечкой памяти в Tomcat и других средах с горячим повторным развертыванием на основе ClassLoader. Пожалуйста, посмотрите на зеленое поле здесь и ссылки оттуда.
(и, пожалуйста, обновите до последней версии, 0.9.5-pre8. это новые функции, и я не помню, в какой предварительной версии 0.9.5 они появились.)
Комментарии:
1. Я вообще удалил зависимость c3p0, и утечки все еще существуют. «Зеленый ящик» был изучен снова и не помог. Я создал тему гибернации для такого рода утечек: forum.hibernate.org/viewtopic.php?f=1amp;t=1035073