Профилировщики баз данных и ввода/вывода
157C# и .NET Framework --- Оптимизация приложений .NET Framework --- Профилировщики баз данных и ввода/вывода
Ранее мы уже рассмотрели вопросы профилирования нагрузки на CPU, времени и памяти. Именно эти характеристики являются наиболее важными с точки зрения оптимизации производительности приложений. Однако существуют и другие характеристики, для измерения которых существуют отдельные инструменты, в этой статье мы коротко упомянем некоторые из них.
Профилировщики доступа к данным и базам данных
Многие управляемые приложения в своей работе опираются на использование базы данных и немалую часть времени тратят на ожидание результатов запросов или на выполнение массивных изменений. Профилирование операций с базами данных может выполняться в двух направлениях: со стороны приложений, с помощью профилировщиков доступа к данным, и со стороны баз данных, с помощью профилировщиков баз данных.
Для работы профилировщиков баз данных часто требуется поддержка со стороны производителей, и такие профилировщики обычно используются администраторами баз данных. Мы не будем касаться профилировщиков баз данных; желающие могут поближе познакомиться с профилировщиком SQL Server Profiler, весьма мощным инструментом профилирования баз данных для Microsoft SQL Server, по адресу: SQL Server Profiler.
Профилировщики доступа к данным, напротив, предназначены для использования разработчиками приложений. Эти инструменты применяются для исследования производительности слоя доступа к данным в приложениях (Data Access Layer, DAL) и обычно сообщают следующую информацию:
запросы, выполняемые приложением, и точную трассировку стека для каждой операции;
список методов приложения, выполняющих операции с базой данных, и список запросов, выполняемых каждым методом;
предупреждения о неэффективных приемах доступа к базе данных, таких как выполнение запросов, не ограничивающих возвращаемый набор результатов, извлечение всех полей из таблицы, когда в приложении используются только некоторые из них, выполнение запросов со слишком большим количеством соединений таблиц или наличие одного запроса на извлечение сущности, связанной с N других сущностей, порождающий запросы для каждой из этих связанных сущностей (эта проблема известна под названием «проблема SELECT N+1»).
Существует несколько коммерческих инструментов профилирования доступа к данным из приложений. Некоторые из них работают только с базами данных определенных типов (такими как Microsoft SQL Server), другие - только с определенными фреймворками доступа к данным (такими как Entity Framework). Ниже перечислены некоторые из них:
- RedGate ANTS Performance Profiler
Способен профилировать запросы к Microsoft SQL Server.
- Инструмент Tier Interactions
Имеется в составе Visual Studio - способен профилировать любые асинхронные операции доступа к данным из ADO.NET - к сожалению, он не поддерживает трассировку стека вызовов для операций с базами данных.
- Hibernating
Семейство профилировщиков под разные платформы (LINQ in SQL Profiler, Entity Framework Profiler и NHibernate Profiler) - способны профилировать все операции с конкретным фреймворком доступа к данным.
Мы не будем вдаваться в подробное обсуждение этих профилировщиков, но если вас волнует проблема производительности вашего слоя доступа к данным, рассмотрите возможность использования этих инструментов совместно с профилировщиками времени или памяти.
Профилировщики конкуренции
Все возрастающая популярность параллельного программирования подтолкнула разработчиков к созданию специализированных профилировщиков приложений, использующих большое количество потоков выполнения, которые могут выполняться на разных процессорах. Позже мы исследуем некоторые ситуации, в которых немалого прироста производительности легко можно добиться лишь за счет распараллеливания операций, и этот прирост производительности лучше всего может быть оценен с помощью точных инструментов измерения.
Профилировщик Visual Studio, в режимах Concurrency (Данные конфликтов ресурсов (параллелизм)) и Concurrency Visualizer (Визуализатор параллелизма), использует события ETW для мониторинга производительности многопоточных приложений и предоставляет отчет с несколькими весьма полезными представлениями, упрощающими узкие места, отрицательно сказывающиеся на масштабируемости и производительности. Он имеет два режима работы, как показано ниже.
В режиме Concurrency (Данные конфликтов ресурсов (параллелизм)) выявляются ресурсы, такие как управляемые блокировки, на которых потоки выполнения в приложении останавливаются в ожидании их освобождения. Первая часть отчета описывает сами ресурсы и потоки выполнения, которые были заблокированы на них - она поможет найти и устранить недостатки, мешающие масштабированию:
Как видно на рисунке, существует несколько потоков выполнения, ожидающих доступа к ресурсу. При выборе потока выполнения, в нижней части отображается его стек вызовов.
Другая часть отчета отображает информацию о конфликтах для конкретного потока выполнения, то есть перечень различных механизмов синхронизации, на которых поток выполнения вынужден был простаивать - она поможет уменьшить задержки на пути выполнения определенного потока. Чтобы запустить профилировщик в этом режиме, выберите пункт меню Analyze --> Launch Performance Wizard (Анализ --> Запустить мастер производительности) и затем выберите радиокнопку Concurrency (Данные конфликтов ресурсов (параллелизм)).
На основании этого отчета можно заключить, что работа распределяется между потоками неравномерно.
В режиме визуализации параллелизма отображается график выполнения всех потоков приложения, где цветом обозначается текущее состояние. Каждый поток имеет несколько переходных состояний - блокировка на операции ввода/вывода, ожидание на механизме синхронизации, выполнение - которые фиксируются профилировщиком, а также стек вызовов. Эти отчеты очень удобно использовать, чтобы понять особенности работы потоков выполнения и выявить причины низкой производительности, такие как чрезмерное количество потоков выполнения, недостаточное количество потоков выполнения и чрезмерное использование механизмов синхронизации.
В графике имеется также встроенная поддержка механизмов Task Parallel Library, таких как параллельные циклы (parallel loops) и механизмы синхронизации CLR. Чтобы запустить профилировщик в этом режиме выберите нужный пункт в подменю Analyze --> Concurrency Visualizer (Анализ --> Визуализатор параллелизма).
На сайте MSDN собрана коллекция антишаблонов программирования многопоточных приложений, выявленных с помощью визуализатора параллелизма, включая колонны блокировок (lock convoy), неравномерное распределение рабочей нагрузки, чрезмерное количество потоков выполнения и другие. При проведении собственных испытаний, вы легко сможете идентифицировать похожие проблемы, визуально сравнив имеющиеся у вас графики с графиками на сайте MSDN.
Профилирование и визуализация работы многопоточных приложений - весьма полезные возможности и мы вернемся к ним в последующих статьях. Они могут служить еще одним ярким подтверждением огромной гибкости механизма ETW - эта вездесущая инфраструктура мониторинга используется самыми разными инструментами профилирования.
Профилировщики ввода/вывода
Последняя характеристика, которую мы рассмотрим - это операции ввода/вывода. События ETW могут использоваться для получения информации об операциях доступа к физическому диску, ошибках получения дисковых страниц из памяти, получении сетевых пакетов и других видах ввода/вывода.
Sysinternals Process Monitor - это бесплатный инструмент, выполняющий сбор информации об операциях с файловой системой и с сетью. Загрузить полный комплект инструментов Sysinternals или только последнюю версию Process Monitor можно на сайте проекта TechNet, по адресу: technet.microsoft.com/ru-ru/sysinternals/bb545021.aspx. Используя его богатые возможности фильтрации, системные администраторы и специалисты, занимающиеся вопросами производительности, смогут проанализировать ошибки, связанные с вводом/выводом (такие как отсутствие файлов или недостаточность привилегий), а также проблемы производительности (такие как попытки доступа к удаленной файловой системе или слишком частое вытеснение страниц памяти в файл подкачки).
Инструмент Process Monitor отображает в главном представлении события нескольких типов и способен выводить стек вызовов для конкретных событий в отдельном диалоговом окне. Кадры стека с номером 19 и ниже - это управляемые кадры.
Proccss Monitor поддерживает полную трассировку стека в режиме ядра и в режиме пользовательского приложения для каждого события, что идеально подходит для поиска избыточных или ошибочных операций ввода/вывода и их местоположений в исходном коде приложения. К сожалению, на момент написания этих строк, инструмент Process Monitor не поддерживал управляемые стеки вызовов, но он способен указать хотя бы общее направление поисков проблем в приложениях, выполняющих операции ввода/вывода.