Анализ дампа кучи с утечкой SSLSocketImpl

У меня есть приложение, которое работает на Amazon EC2 (с использованием нескольких продуктов AWS, таких как S3, DynamoDB и т. Д.) И имеет утечку памяти. Я собрал несколько дампов кучи и прогнал их с помощью Eclipse Memory Analyzer Tool, который определил несколько сотен экземпляров sun.security.ssl.SSLSocketImpl (занимающих десятки МБ памяти) как вероятные утечки.

Однако мне сложно понять, почему эти SSLSocketImpl объекты не были утилизированы.

большинство экземпляров SSLSocketImpl в дампах имеют две ссылки: одну из java.lang.ref.Finalizer, а другую - из com.amazonaws.internal.SdkSSLSocket. поток финализатора в моем дампе кучи сообщается как бездействующий, без объектов, ожидающих завершения. но объекты com.amazonaws.internal.SdkSSLSocket, которые ссылаются на утечку SSLSocketImpl объектов, похоже, были очищены. по крайней мере, я не могу их найти на свалке (вид Dominator в MAT).

Я новичок в анализе дампов кучи java. что мне искать дальше? если объекты Amazon SdkSSLSocket действительно были очищены, почему объекты SSLSocketImpl также не были очищены?

Благодарность!


person ur-vogel    schedule 06.12.2016    source источник
comment
Вы что-то нашли?   -  person skirsch    schedule 22.05.2017
comment
никогда не дошел до корня этого. его не выпускают уже несколько месяцев, поскольку побочным эффектом развертывания новых экземпляров является устранение проблем с утечкой памяти.   -  person ur-vogel    schedule 23.05.2017
comment
какие инстансы EC2 вы использовали?   -  person skirsch    schedule 31.05.2017


Ответы (2)


Думаю, я тоже столкнулся с этим. Немного поработав с MAT, я смог определить причину того, что происходит, или, по крайней мере, предотвратить выполнение G1GC полной сборки мусора на закрепленном пространстве. Вот диаграмма мата, на которую я смотрел:

введите описание изображения здесь

Мое приложение представляет собой простой реактивный HTTP-сервер с загрузкой Spring, на котором прокси-сервер имеет разумный объем вызовов чтения базы данных. Я запускал один процессор в контейнере докеров на K8s с примерно 4 ГБ памяти. Я удвоил это до 8 ГБ памяти и все еще видел проблему.

Я не поверил, что это была утечка памяти, потому что я мог наблюдать, как полный сборщик мусора может очистить закрепленное пространство, это займет некоторое время.

Я считаю, что JDBC делает то, что когда TCP-соединения прекращаются, они переводятся в поток под названием AbandonedConnectionCleanupThread.

So what the solution turned out to be was just giving the JVM an extra CPU to service the AbandonedConnectionCleanupThread.

Как только я это сделал, размер моего постоянного пространства никогда не увеличивался, а g1_old_space вырастал примерно до размера постоянного пространства, однако мой G1 может очищать g1_old_space более эффективно, чем постоянные, поэтому длительные паузы приложений исчезли, и G1 уважал мои - XX: MaxGCPauseMillis

person Jordan Shaw    schedule 20.05.2020

Возможно, это связано с тем, что не задан размер кеша сеанса SSL, который по умолчанию бесконечен и может привести к потреблению огромного объема кучи. Установка javax.net.ssl.sessionCacheSize = 1000 должна помочь.

person Vaishnavi Ramesh Jayaraman    schedule 24.06.2019