Почему GCC предупреждает меня о провале, даже когда я использую [[провал]]?


86

В следующем фрагменте кода я использую стандартный [[fallthrough]]атрибут из C ++ 1z для документирования того, что требуется падение:

#include <iostream>

int main() {
    switch (0) {
        case 0:
            std::cout << "a\n";
            [[fallthrough]]
        case 1:
            std::cout << "b\n";
            break;
    }
}

С GCC 7.1 код компилируется без ошибок. Однако компилятор все равно предупреждает меня о провале:

warning: this statement may fall through [-Wimplicit-fallthrough=]
    std::cout << "a\n";
    ~~~~~~~~~~^~~~~~~~

Зачем?


33
И вот я тут подумал, что вы, ребята, C ++, не сможете сделать что-то еще более уродливым!
SnakeDoc

3
@SnakeDoc: Это подарок!
Дедупликатор

3
@SnakeDoc Это должен быть комментарий к ответу, что делает его еще хуже. :)

23
Я не согласен с закрытым голосованием. Причина «простой типографской ошибки» существует для случаев, когда проблема с OP возникла только из-за некоторой ошибки, не связанной с описанием вопроса, и не будет полезна для кого-либо еще. В этом случае вполне вероятно, что другие люди забудут точку с запятой в этом месте, получат ту же ошибку и найдут этот вопрос при поиске решения.
CodesInChaos

14
Мне очень не нравится, что мой комментарий был удален из этого вопроса, поэтому я вынужден повторить его снова - хотя это действительно типографская ошибка, очень вероятно, что другие пользователи будут повторять его, искать его и находить этот вопрос с этим ответом. Таким образом, это хороший вопрос и хороший ответ, и его следует оставить открытым.
Barry

Ответы:


105

После атрибута отсутствует точка с запятой:

case 0:
    std::cout << "a\n";
    [[fallthrough]];
    //             ^
case 1:

[[fallthrough]]Атрибут должны быть применен к пустому оператору (см P0188R1 ). В этом случае текущий ствол Clang дает полезную ошибку :

error: fallthrough attribute is only allowed on empty statements
    [[fallthrough]]
      ^
note: did you forget ';'?
    [[fallthrough]]
                   ^
                   ;

Обновление: Коди Грей сообщил об этой проблеме команде GCC.


Было бы неплохо упомянуть, к чему применяется атрибут, без точки с запятой. Полагаю, дело в следующем?
CodesInChaos

2
@CodesInChaos fallthrough attribute is only allowed on empty statements; поскольку за ним не следует пустое выражение, gcc просто игнорирует его
musicman523

2
@ musicman523 Это ... кажется ... неправильным? По-видимому, было бы более разумным потребовать точку с запятой, даже если за ней следует пустой оператор, и просто отказаться от компиляции в противном случае.
SnakeDoc

@SnakeDoc По-видимому, это просто частный случай атрибутов оператора, поэтому синтаксический анализатор разрешает это, но он не имеет никакой семантики при применении к непустому оператору. Считайте это ошибкой, если хотите, и clangисправьте ее.
Barmar

2
@CodesInChaos Без точки с запятой атрибут будет принадлежать метке.
TC
Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.