Цель _never_executed()?
Я видел этот макрос, определенный ранее, но никогда не знал его цели. Кто-нибудь может пролить свет на это?
4 ответа
Это встроенная функция компилятора, обычно используемая во встроенном программировании. Единственный раз, когда я видел, что он использовался, это "по умолчанию" для оператора switch, чтобы утверждать, что переменная имеет ограниченный диапазон (для лучшей оптимизации). Пример:
/* Get DTMF index */
switch(dtmf)
{
case '0':
case '1':
case '2':
case '3':
case '4':
case '5':
case '6':
case '7':
case '8':
case '9':
/* Handle numeric DTMF */
index = dtmf - '0';
break;
case 'A':
case 'B':
case 'C':
case 'D':
index = dtmf - 'A' + 10;
break:
default:
_never_executed();
break;
}
Вероятно, не работает со всеми компиляторами...
Как FYI, MSVC имеет нечто подобное (с немного большей гибкостью), __assume()
внутренняя. Один пример, который они дают:
int main(int p)
{
switch(p){
case 1:
func1(1);
break;
case 2:
func1(-1);
break;
default:
__assume(0);
// This tells the optimizer that the default
// cannot be reached. As so, it does not have to generate
// the extra code to check that 'p' has a value
// not represented by a case arm. This makes the switch
// run faster.
}
}
Я не уверен, какая версия MSVC была впервые поддержана.
Я не видел этого раньше, но STFW с Google сначала задают этот вопрос, а затем некоторые другие ссылки. Из того, что он говорит, компилятор явно намекает на то, что код никогда не выполняется - так что компилятор может выполнять оптимизацию. Это вполне может рассматриваться как оправдание для установки "assert(0)" вместо него - поскольку код никогда не будет выполнен, утверждение никогда не сработает. Конечно, если утверждение срабатывает, то вы знаете, что у вас есть проблема.
См. Также классическую статью "Не может случиться, или /* NOTREACHED */, или ядро дампа реальных программ".
Стоит прочитать, даже сейчас.
Я видел такие вещи раньше как часть тестирования. Если он выполняется, то вы знаете, что у вас есть ошибка.