refal-5-lambda
refal-5-lambda copied to clipboard
Подавление предупреждений
Задача всплыла в комментариях к #290. Процитирую:
Допустим, компилятор выявил связанную переменную в образце, показал на неё программисту. Программист смотрит и говорит: «Спасибо компилятор, я именно это и имел ввиду», т.к. там действительно должна быть повторная переменная (как в случае с синтаксическими деревьями в заглавном посте).
Поэтому нужен способ подавлять предупреждения компилятора для ложноположительных случаев.
Предлагается такой способ — комментарий
/* same */
, который ставится в той же строчке. Комментарий распознаётся лексическим анализатором, он выдаёт токен-подавитель (TkSuppressor
), который помещается в список ошибок. Список ошибок при печати удаляет предупреждение-Wrepeat-variable
(так мы его назовём) в тех же номерах строк, что и комментарий-подавитель.В принципе, можно предусмотреть общую форму подавителей вида
/* SUPPRESS: -Wwarning-name */
, подавляющую любое предупреждение в данной строке. Но для данного случая удобнее использовать специальный комментарий/* same */
(без учёта регистра и пробельных символов).
Мотивация
Сформулируем точнее. Задача #290 предполагает написание относительно ненадёжного предупреждения, которое будет выдавать ложные срабатывания. Предлагается добавить комментарий /* same */
для его подавления.
Также очевидно, что ложные срабатывания в принципе могут быть на любые предупреждения, не только на это. Для их выборочного подавления нужен более общий механизм, т.е. более общий комментарий вида /* SUPPRESS: -Wname */
.
Подавление предупреждений на участке кода — распространённая потребность, многие компиляторы C/C++ имеют специальные конструкции для этой цели. Как правило, они оформлены как прагмы (#pragrma
). Прагмы C/C++, подавляющие предупреждения, действуют от строки, где они записаны до следующей прагмы, отменяющей действие предыдущей.
Подобные многострочные подавители предупреждений можно реализовать как псевдокомментарии (*$SUPPRESS -Wname
), однако пока не очевидно, есть ли в них потребность. Т.к. потребность не очевидна, реализовывать их не будем.
Реализация
Комментарии-подавители транслируются в особого рода токены, которые затем помещаются в список ошибок. Затем уже на уровне списка ошибок подавители стирают предупреждения, указанные в тех же строках. Комментарий может как предшествовать позиции предупреждения, так и быть после неё. В частности, комментарий /* same */
может как предварять повторную переменную, так и следовать за ней или вообще располагаться в самом конце строки.