фоновое объяснение
Недавно одноклассники QC обнаружили в процессе запуска игры, что игра вылетает после долгой игры.После сбора информации функциональная ошибка была исключена.
1. Определите, является ли это утечкой памяти
Получите настоящую машину, подключите USB, отключите избыточные фоновые процессы, откройте Perfdog, следующая операция будет столь же свирепой, как тигр, конкретная операция Perfdog не будет повторяться, руководство по использованию perfdog можно найти здесь.
Получите график тренда памяти
использовать мобильный телефон
Как только отображается это изображение, можно сделать вывод об утечке памяти.Это диаграмма динамики памяти при нормальной игре и запуске игры в течение 30 минут;
Вывод: Память продолжает подниматься и имеет место утечка памяти.
В отличной игре память обычно увеличивается и уменьшается, и многократное выполнение одной и той же функции не приведет к тому, что функция памяти продолжит увеличиваться;
Показывает взлеты и падения, такие как:
Зная, что есть утечка памяти, давайте начнем анализировать, где может быть вызвана утечка памяти;
2. Проанализируйте причину утечки
Как правило, для игр Unity узким местом памяти являются ресурсы и память кучи Mono, две части;
Ниже приведен обзор распределения памяти в программе Unity Game во время выполнения.
Давайте сначала кратко представим Mono. Unity использует механизм Mono для выполнения кросс-платформенных операций, точно так же, как JAVA использует виртуальные машины для выполнения кросс-платформенных операций. Mono также является кросс-платформенной реализацией. Принцип кроссплатформенной реализации заключается в использовании набора кодовых инструкций под названием CIL (Common Intermediate Language, также известный как MSIL Microsoft Intermediate Language).CIL может работать в любой среде, поддерживающей CLI (Common Language Infrastructure).Как и .NET. — это реализация Microsoft этого стандарта, а Mono — еще одна реализация CLI. Поскольку CIL может работать во всех средах, поддерживающих CLI, таких как только что упомянутая среда выполнения .NET и среда выполнения Mono, то есть он не имеет ничего общего с конкретными платформами или процессорами.
Как правило, для игр, разработанных Unity, накладные расходы памяти связаны со следующими тремя аспектами:
1. Занятие ресурсной памяти;
2. Использование памяти самого модуля двигателя;
3. Управляемое использование памяти кучи.
Mono управляет памятью через механизм сборки мусора (GarbageCollect, называемый GC), может автоматически изменять размер кучи, чтобы адаптироваться к нужному вам объему памяти, и может своевременно вызывать операцию сборки мусора (GarbageCollection), чтобы освободить память. память, которая больше не нужна. То есть Mono автоматически освободит часть памяти, но следует отметить, что память, освобожденная GC, будет использоваться только mono и не будет возвращена операционной системе, поэтому память моно кучи будет только увеличиваться и не уменьшаться.
Вот краткое введение в принцип переработки Mono:
Mono будет отслеживать действие каждого выделения памяти и поддерживать таблицу объектов распределения.При GC он берет глобальную область данных и объект в текущем регистре в качестве корневого узла и проходит в соответствии с эталонным отношением.Для каждого пройденного объекта Отметить как живое. Отметка всех объектов означает, что доступ к объекту возможен через глобальный объект или текущий контекст, а неотмеченный объект означает, что доступ к объекту невозможен никакими средствами, то есть объект «отключен», и GC будет в конечном итоге вся «отключенная» память объекта восстанавливается.
определение утечки памяти
Мы называем ситуацию, когда объект больше не нужен, но не собирается сборщиком мусора, утечкой монопамяти. Утечки монофонической памяти уменьшат свободную память, частый сборщик мусора и постоянное расширение монокучи, что в конечном итоге приведет к увеличению использования игровой памяти. В конце концов памяти становится слишком много, и процесс завершается или аварийно завершается операционной системой. Проще говоря, некоторые объекты не освобождаются после создания экземпляра, один хранится в памяти, и новые объекты должны обращаться за новым пространством памяти, что приводит к постоянному увеличению памяти.
ключевой фокус
Использование профилей, текстур, мешей, RenderTextures и систем частиц;
Например, следует ли использовать пул объектов для частого создания и уничтожения объектов, или ресурсы, такие как частицы и текстуры, освобождаются из памяти во времени после их отображения и т. д.;
3. Методы испытаний
1. Сначала запустите тест, чтобы определить проблему и установить причину.Например, я определил, что есть утечка памяти, запустив игру выше;
2. Сузить масштаб.Поскольку сцена игры сложна во время процесса запуска, вышеприведенный совместный запуск не может точно определить проблему, поэтому нам нужно разделить тест сцены.Например, я включаю следующие сцены в приведенный выше запущенная игра, открытие и закрытие Если нет очевидных данных об интерфейсе пользовательского интерфейса, сцене боя, переключении карты, обновлении оружия и т. д., то проверьте следующие сценарии соответственно. Например, сцена пользовательского интерфейса может многократно открывать и закрывать интерфейс пользовательского интерфейса, сцена битвы может продолжать зависать в бою, многократно переключать карту и т. д. Короче говоря, поведение в игре снижается, а сцена должна быть обнаружена. утонченный;
3. Проблемы с позиционированием
Если в сцене происходит утечка памяти, запустите игру, обнаружив эту сцену, и когда игра запущена, соответствующий движок также имеет некоторые инструменты для проверки использования конкретного кода, такие как профайлер Unity.
Если есть утечки памяти в нескольких сценариях, необходимо найти пересекающиеся части этих сценариев, такие как коммуникационная структура и т. д. На этот раз, после тестирования нескольких сценариев, было обнаружено, что утечки были.Наконец, после расследования, было обнаружено, что используемая коммуникационная структура дает утечку.
Четыре, введение, связанное с памятью Perfdog
Обычно существует четыре типа данных, которые Android может легко получить в памяти, и мы также можем получить их через ADB.
VSS — потребление виртуальной памяти Virtual Set Size (включая память, занимаемую разделяемыми библиотеками)
RSS — Размер резидентного набора фактически использует физическую память (включая память, занятую разделяемыми библиотеками).
PSS — Proportional Set Size фактическая используемая физическая память (пропорциональное распределение памяти, занятой разделяемыми библиотеками)
USS — физическая память, занятая только процессом уникального набора размеров (исключая память, занятую общей библиотекой).
Вообще говоря, размер используемой памяти выглядит следующим образом: VSS >= RSS >= PSS >= USS
А память Perfog — это память Android PSS, которая также является данными, которые мы обычно используем для представления памяти, и фактически используемым размером физической памяти.
Swap Memory (Подкачка памяти, некоторые устройства поддерживают функцию Swap. После включения функции Swap система будет сжимать память PSS. Если Swap увеличивается, PSS соответственно уменьшается. Поскольку сжатие будет занимать ресурсы ЦП, FPS соответственно уменьшится.)
Виртуальная память (VSS) Виртуальная память — это технология управления памятью компьютерной системы. Это заставляет приложение думать, что оно имеет непрерывную доступную память (непрерывное полное адресное пространство), тогда как на самом деле оно обычно разделено на несколько фрагментов физической памяти, а некоторые временно хранятся на внешнем дисковом хранилище, когда необходим обмен данными.
5. Предварительное изучение новых функций Perfdog
Только что запущена PerfDog версии 3.5, в которой добавлено новое значение «Использование ЦП (нормализованное»): нормализованное использование ЦП.
Официальное объяснение:
Традиционный метод расчета: при текущей частоте ЦП загрузка ЦП = время выполнения ЦП / общее время ЦП.
Поскольку частота ЦП мобильных устройств время от времени меняется, при использовании традиционного метода расчета загрузки ЦП предполагается, что загрузка ЦП рассчитывается при низкой частоте = 30%, а загрузка ЦП рассчитывается при высокой частоте ЦП = 30. %. Те же 30%, но расход производительности совсем другой, да и расход высоких частот явно выше. Традиционное использование ЦП больше не может точно отражать потребление производительности.
Поэтому нам нужен нормализованный (количественный) способ статистики. Учитывайте частотный фактор.
Загрузка ЦП (нормализованная) = (время выполнения ЦП/общее время ЦП) * (сумма всех частот ЦП на текущий момент/сумма максимальных значений всех частот ЦП).
PerfDog имеет два статистических метода. Загрузка ЦП по умолчанию соответствует нормализованной загрузке ЦП. В качестве меры производительности рекомендуется использовать нормализованную загрузку ЦП.
Подробное описание можно найти здесь:Нормализовать загрузку ЦП
Попробуйте ниже. Процесс использования теста такой же, как и раньше. Давайте посмотрим на новое сравнение данных
заглавие:
Сравнение графика тренда использования ЦП:
Сравнение диаграммы тенденций использования ядра ЦП:
Судя по графику тренда, на самом деле между двумя алгоритмами нет большой разницы, но разница будет более очевидной, когда она точно соответствует скорости использования конкретного кадра.С точки зрения чисто производительности, традиционное использование ЦП может быть рассчитан только с числовой точки зрения.Он отражает использование ЦП мобильного телефона, но не может выразить эффективность использования ЦП мобильного телефона с точки зрения использования производительности.Как упоминалось выше, коэффициент использования ЦП = 30 % при низкой частоте, а загрузка ЦП при высокой частоте ЦП = 30%. Те же 30%, но расход производительности совсем другой. Этот недостаток может компенсировать нормализация показателей загрузки ЦП. Текущая индустрия тестирования смешана с хорошим и плохим, и нормативных показателей мало, и было бы хорошо, если бы отраслевой стандарт можно было унифицировать.