Код на C # очень медленный с отладчиком;Ошибка MemoryMappedFile? - PullRequest
9 голосов
/ 20 октября 2011

У меня есть приложение клиент / сервер. Серверный компонент работает, использует WCF в режиме «удаленного взаимодействия» (двоичный форматер, объекты сеанса).

Если я запускаю серверный компонент и запускаю клиент, первая задача, которую сервер выполняет, завершается за <0,5 с. </p>

Если я запускаю серверный компонент с подключенным отладчиком VS, а затем запускаю клиент, выполнение задачи занимает более 20 секунд.

Нет изменений кода - нет изменений условной компиляции. То же самое происходит, если у меня серверный компонент скомпилирован и запущен в 32-битном, 64-битном режиме с процессом размещения VS, без процесса размещения VS, или с какой-либо комбинацией этих вещей.

Возможно, важно : если я использую VS.NET profiler (режим выборки), то приложение запускается так быстро, как если бы не было отладчика. Поэтому я не могу диагностировать это таким образом. Только что проверил, режим КИП также работает быстро. То же самое для режима профилирования параллелизма, работает быстро.

Ключевые данные:

  • Приложение использует довольно интенсивную многопоточность (40 потоков в стандартном пуле потоков). Создание потоков происходит быстро независимо и не является медленной точкой. Есть много замков, WaitHandle с и Monitor узоров
  • Приложение вообще не вызывает исключений.
  • Приложение не создает вывод консоли.
  • Приложение полностью управляется кодом.
  • Приложение отображает несколько файлов на диске в MemoryMappedFile: 1x750MB и 12x8MB и несколько меньших

Измеренная производительность:

  • Использование ЦП минимально в обоих случаях; когда отладчик подключен, загрузка процессора составляет <1% </li>
  • Использование памяти минимально в обоих случаях; возможно 50 или 60 МБ в обоих случаях
  • Существует множество сбоев страниц (ref MMF), однако они возникают медленнее, когда подключен отладчик
  • Если процесс размещения VS не используется или, по сути, вступает в игру «монитор удаленной отладки», то , что использует приличное количество ЦП и создает большое количество сбоев страниц. Но это не единственный раз, когда возникает проблема
  • Разница в производительности видна независимо от того, как работает клиент. Единственная изменяемая переменная - это компонент сервера, запускаемый с помощью «Начать с отладки» и запускаемый из Проводника.

Мои идеи:

  • WCF медленный при отладке?
  • MemoryMappedFiles замедляется при отладке?
  • Использовано 40 потоков - медленно отлаживать? Возможно, мониторы / блокировки уведомляют отладчик? Планирование потоков становится странным / переключение контекста очень редко?
  • Космическое фоновое излучение, придающее разум и жестокое чувство юмора ВС

Все кажутся глупо маловероятными.

Итак, мои вопросы:

  1. Почему это происходит?
  2. Если № 1 неизвестен, как я могу диагностировать / выяснить?

Ответы [ 2 ]

9 голосов
/ 20 октября 2011

Исключения могут заметно повлиять на производительность приложения. Существует два типа исключений: исключения первого шанса (изящно обработанные с помощью блока try / catch) и необработанные исключения (которые в конечном итоге приведут к падению приложения).

По умолчанию отладчик не показывает исключения с 1-й случайностью, он просто показывает необработанные исключения. И по умолчанию он также показывает только исключения, возникающие в вашем коде. Однако, даже если он не показывает их, он все равно обрабатывает их, поэтому на его производительность может повлиять (особенно в нагрузочных тестах или при выполнении большого цикла).

Чтобы включить отображение исключений 1-го шанса в Visual Studio, нажмите «Отладка | Исключения», чтобы вызвать диалоговое окно «Исключения», и отметьте «Брошенный» в разделе «Общее время выполнения» (вы можете быть более конкретным и выбрать 1-й шанс). исключение, которое вы хотите увидеть).

Чтобы включить отображение исключений 1-го шанса, происходящих из любой точки приложения, а не только из вашего кода, нажмите «Инструменты | Параметры | Отладка | Общие» и отключите параметр «Включить только мой код».

И для этих конкретных случаев «режима криминалистики» я также настоятельно рекомендую включить .NET Framework Source Stepping (для этого необходимо отключить «Enable Just My Code»). Очень полезно понимать, что происходит, иногда просто смотреть на стек вызовов очень вдохновляюще - и особенно полезно в случае смешения космического излучения: -)

Две похожие интересные статьи:

5 голосов
/ 25 апреля 2016

Поскольку это один из первых результатов поиска этой проблемы, я хотел бы добавить свое решение проблемы в надежде сэкономить 2 часа на исследованиях, как в моем случае.

Мой код замедлился с 30 секунд без отладчика до 4 минут с отладчиком.потому что я забыл удалить условную точку останова.Похоже, что они сильно замедляют выполнение, так что следите за этими

...