Перейти к основному содержимому

Один небольшой шаг для Chrome, один гигантский скачок для V8

· 2 мин. чтения
хранители кучи Улан Дегенбаев, Ханнес Пайер, Михаэль Липпаутц и воин DevTools Алексей Козятинский

V8 имеет жесткий лимит на размер своей кучи. Это служит защитным механизмом против приложений с утечками памяти. Когда приложение достигает этого жесткого лимита, V8 выполняет серию последнего шанса сборок мусора. Если сборки мусора не помогают освободить память, V8 прекращает выполнение и сообщает об ошибке недостатка памяти. Без жесткого лимита приложение с утечкой памяти могло бы использовать всю системную память, что повредило бы производительность других приложений.

Ирония заключается в том, что этот защитный механизм затрудняет расследование утечек памяти для разработчиков JavaScript. Приложение может выйти за пределы памяти до того, как разработчик сможет исследовать кучу в DevTools. Более того, сам процесс DevTools может выйти за пределы памяти, потому что он использует обычный экземпляр V8. Например, создание снимка кучи этого демо завершает выполнение из-за недостатка памяти в текущей стабильной версии Chrome.

Исторически лимит кучи V8 был удобно установлен так, чтобы соответствовать диапазону знаковых 32-битных целых чисел с некоторым запасом. Со временем это удобство привело к небрежному коду в V8, который смешивал типы различной ширины бит, фактически разрушая возможность увеличения лимита. Недавно мы очистили код сборщика мусора, что позволило использовать более крупные размеры кучи. DevTools уже использует эту возможность, и создание снимка кучи в упомянутом ранее демо работает как ожидается в последней версии Chrome Canary.

Мы также добавили функцию в DevTools для приостановки приложения, когда оно находится вблизи недостатка памяти. Эта функция полезна для расследования ошибок, которые вызывают выделение большого количества памяти за короткий промежуток времени. При запуске этого демо с последней версией Chrome Canary, DevTools приостанавливает приложение перед ошибкой недостатка памяти и увеличивает лимит кучи, предоставляя пользователю возможность исследовать кучу, оценить выражения в консоли для освобождения памяти, а затем возобновить выполнение для дальнейшей отладки.

Встроенные механизмы V8 могут увеличить лимит кучи с помощью функции set_max_old_generation_size_in_bytes API ResourceConstraints. Но будьте осторожны, некоторые стадии в сборщике мусора имеют линейную зависимость от размера кучи. Паузы сборки мусора могут увеличиться с более крупными размерами кучи.