メインコンテンツ

MISRA C:2012 Rule 15.6

The body of an iteration-statement or a selection-statement shall be a compound statement

説明

ルール定義

The body of an iteration-statement or a selection-statement shall be a compound- statement 1 .

根拠

反復ステートメントまたは選択ステートメントに関連付けられたコード ブロックが中かっこで囲まれていない場合、関連付けで間違える可能性があります。以下に例を示します。

  • インデントが原因で、コード行を反復ステートメントまたは選択ステートメントに誤って関連付ける。

  • 反復ステートメントまたは選択ステートメントの後に誤ってセミコロンを付ける。意図に反して、セミコロンが原因でステートメントの後に続く行がステートメントと関連付けられなくなります。

このチェッカーは、本体に 1 行しか含まれていない場合でも選択ステートメントまたは反復ステートメントの後ろに中かっこを追加するという慣例に従います。後で、新しい行が追加されたときに、それらを追加した開発者が中かっこがないことに気付いてそれらを含める必要がなくなります。

Polyspace 実装

チェッカーは、次のように、for ステートメントに続く最初のトークンが左中かっこではない for ループにフラグを設定します。

for (i=init_val; i > 0; i--)
   if (arr[i] < 0)
      arr[i] = 0;
同様のチェックが、ifelse ifelseswitchfor、および do..while ステートメントに対して実施されます。

[結果の詳細] ペイン上のメッセージの 2 行目は、どのステートメントがルールに違反しているかを示します。たとえば、前述の例には 2 つの違反があります。メッセージの 2 行目は、1 つの違反について for ループを指し、もう 1 つの違反について if 条件を指します。

レポート内の追加のメッセージ

  • The else keyword shall be followed by either a compound statement, or another if statement.

  • An if (expression) construct shall be followed by a compound statement.

  • The statement forming the body of a while statement shall be a compound statement.

  • The statement forming the body of a do ... while statement shall be a compound statement.

  • The statement forming the body of a for statement shall be a compound statement.

  • The statement forming the body of a switch statement shall be a compound statement.

トラブルシューティング

ルール違反を想定していてもその違反が表示されない場合、コーディング規約違反が想定どおりに表示されない理由の診断を参照します。

すべて展開する

int data_available = 1;
void f1(void) {
    while(data_available)                 /* Non-compliant */
        process_data();

    while(data_available) {               /* Compliant */
        process_data();
    }
}

この例では、2 番目の while ブロックは中かっこで囲まれており、ルールに違反しません。

#include<stdbool.h>
void f1(bool flag_1, bool flag_2) {
    if(flag_1)                            /* Non-compliant */
        if(flag_2)                        /* Non-compliant */
            action_1();
    else                                  /* Non-compliant */
            action_2();
}

この例では、if または else ブロックは中かっこで囲まれていないため、ルールに違反します。上記のようにインデントされていない限り、else ステートメントを内側の if に関連付けてしまいます。

修正 — 選択ステートメント ブロックを中かっこ内に配置

1 つの修正方法として、if または else ステートメントに関連付けられた各ブロックを中かっこで囲みます。

#include<stdbool.h>
void f1(bool flag_1, bool flag_2) {
    if(flag_1) {                          /* Compliant */
        if(flag_2) {                        /* Compliant */
            action_1();
        }
    }
    else {                                /* Compliant */
        action_2();
    }
}

#include<stdbool.h>
void f1(bool flag_1) {
    while(flag_1);                        /* Non-compliant */
    {
        flag_1 = action_1();
    }
}

この例では、while ステートメントの後に中かっこで囲まれたブロックが続いていても、ルールに違反します。while ステートメントの後のセミコロンにより、ブロックは while ステートメントから分離されます。

ルールはこのような誤ったセミコロンの検出に役立ちます。

チェック情報

グループ: 制御フロー
カテゴリ: 必要
AGC カテゴリ: 必要

バージョン履歴

R2014b で導入


1 All MISRA coding rules and directives are © Copyright The MISRA Consortium Limited 2021.

The MISRA coding standards referenced in the Polyspace® Bug Finder™ documentation are from the following MISRA standards:

  • MISRA C:2004

  • MISRA C:2012

  • MISRA C:2023

  • MISRA C++:2008

  • MISRA C++:2023

MISRA and MISRA C are registered trademarks of The MISRA Consortium Limited 2021.