Комментарии 24
Да уж, век учись, а С++ все равно не выучишь :)
За статью спасибо, прибавилось ясности в работе компилятора!
За статью спасибо, прибавилось ясности в работе компилятора!
+6
Между прочим, на Native x64 edit and continue не работает, так что никакой магии :)
+2
Там же про CLR, не про native C++.
0
Я так понимаю, что это фича Visual Studio, а не CLR, с Native то же самое, если мой английский меня не подводит.
+1
Похоже на то. Просто ваша первая ссылка про CLR совсем, вот я и придрался :)
Не думаю что это можно рассматривать как фичу вижуал студио, т.к. между native и CLR огромная пропасть, так что не обязательно всё поддерживаемое в native есть в CLR, и в некоторых случаях, естественно, наоборот.
Не думаю что это можно рассматривать как фичу вижуал студио, т.к. между native и CLR огромная пропасть, так что не обязательно всё поддерживаемое в native есть в CLR, и в некоторых случаях, естественно, наоборот.
0
Статья интересная, в плане экспериментов :-) надо только пару вещей для начинающих отметить:
1. бенчмарки на debug build делать бессмысленно, он не для скорости предназначен, а для максимума проверок
2. отключать проверки в debug build крайне нежелательно
1. бенчмарки на debug build делать бессмысленно, он не для скорости предназначен, а для максимума проверок
2. отключать проверки в debug build крайне нежелательно
+3
1. Если вы НЕ используете Debug, то бессмысленно. А если с вашим приложением вам же невозможно работать, то имеет смысл бенчмаркить и ускорять Debug — вам же от этого лучше.
+2
Всё-равно не понимаю, зачем в дебаге бенчить? Всё-равно результаты бенча в дебаге неадекватны.
+2
Так дело не в бенче самом (хотя для самого дебага бенчмарк вполне адекватен), а в том, чтобы понять что конкретно тормозит и исправить это.
+1
Бывают случаи, когда из-за таких замедлений дебажный билд вообще теряет целесообразность — на нем невозможно дождаться результата проверок, так что большое спасибо автору за статью, особенно насчет прагм, очень ценная информация.
Единственное название не совсем соответствует, что видимо вас и смутило, статья все же об управлении скоростью дебажного билда.
Единственное название не совсем соответствует, что видимо вас и смутило, статья все же об управлении скоростью дебажного билда.
+2
А иногда не только невозможно дождаться, а просто ничего не работает, например если realtime данные параллельно должны обрабатываться, а они не успевают.
Но в таких случаях ихо проще включить отладочную инфу для релиза, ну и при необходимости оптимизации убрать, вместо того чтобы отключать все дебаг проверки и заморочки. Получится такой дебаг-релиз :)
Но в таких случаях ихо проще включить отладочную инфу для релиза, ну и при необходимости оптимизации убрать, вместо того чтобы отключать все дебаг проверки и заморочки. Получится такой дебаг-релиз :)
0
например если realtime данные параллельно должны обрабатываться, а они не успевают
Хм, а что значит должны — как вы гарантируете, что данные точно обработаются без синхронизации?
0
Удивительно, что проверки под _DEBUG тормозят it++ по сравнению с ++it более чем в 2 раза (3 vs 8). Там добавка-то: объект на стеке создать, копи-конструктор два раза позвать, и деструктор.
В этом свете ещё более удивительно, что положить 256 байт на стек на каждый вызов функции тормозит всего на 20%. В стек положить, конечно, быстро, но по идее данные из-за этого станут нелокальными => промахи кэша. Хотя с другой стороны, в дебаге и так уже всё нелокально шокапец, так что…
А вот за инфу про /ZI отдельное спасибо, будем знать :)
В этом свете ещё более удивительно, что положить 256 байт на стек на каждый вызов функции тормозит всего на 20%. В стек положить, конечно, быстро, но по идее данные из-за этого станут нелокальными => промахи кэша. Хотя с другой стороны, в дебаге и так уже всё нелокально шокапец, так что…
А вот за инфу про /ZI отдельное спасибо, будем знать :)
0
L1 кеш куда больше 256 байт, а стек попадает примерно в одно и то же место при последовательных вызовах. Это около 100 тактов. Кроме того не все вызовы пишут 240 байт, например operator ++ пишет всего 28 байт, для чего делается 7 mov.
Основные тормозища видимо из-за… критической секции в деструкторе отладочного итераторе!
Основные тормозища видимо из-за… критической секции в деструкторе отладочного итераторе!
+1
Понятно, что единоразово 256 байт положить в кэш это не страшно, но «если все так будут делать», то раз-два и нету больше кэша :)
Странно, не замечал чтобы критическая секция сама по себе тормозила, она же на атомиках и только в случае неудачи сваливается на мьютекс. По моим замерам, критическая секция при низкой конкуренции не стоит практически ничего (на уровне вызова функции).
Странно, не замечал чтобы критическая секция сама по себе тормозила, она же на атомиках и только в случае неудачи сваливается на мьютекс. По моим замерам, критическая секция при низкой конкуренции не стоит практически ничего (на уровне вызова функции).
0
Вложенные вызовы убьют кеш конечно. Но тут они последовательные. И записываются одни и те же 256 байт (или меньше). Фактически фрейм растет и заполняется маркерами, но остается маленьким, горячим и полностью в L1.
Под критической секцией я имел в виду еще и всю прикрытую ей работу, а именно _Orphan_me. Там длинная цепочка унаследованных деструкторов, под десяток call-ов, ну и в самом низу защищенное локом обновление списка итераторов контейнера. Те. недешевый сам по себе деструктор вызывается в 3 раза чаще, отчего и основные тормоза.
Под критической секцией я имел в виду еще и всю прикрытую ей работу, а именно _Orphan_me. Там длинная цепочка унаследованных деструкторов, под десяток call-ов, ну и в самом низу защищенное локом обновление списка итераторов контейнера. Те. недешевый сам по себе деструктор вызывается в 3 раза чаще, отчего и основные тормоза.
+1
Мужик
0
Зарегистрируйтесь на Хабре , чтобы оставить комментарий
Учимся правильно бенчмаркать 2: как компилятор бьет в спину