メインコンテンツ

このページの内容は最新ではありません。最新版の英語を参照するには、ここをクリックします。

CERT C: Rule FLP37-C

浮動小数点値の比較にオブジェクト表現を使用しない

説明

ルール定義

浮動小数点値の比較にオブジェクト表現を使用しないようにします。1

Polyspace 実装

ルール チェッカーは、"浮動小数点値のメモリ比較" をチェックします。

すべて展開する

問題

[浮動小数点値のメモリ比較] は、浮動小数点値のオブジェクト表現または浮動小数点メンバーが含まれた構造体のオブジェクト表現を比較する場合に発生します。関数 memcmpbcmp、または wmemcmp を使用してビット パターン比較を実行すると、欠陥が報告されます。

リスク

浮動小数点値のオブジェクト表現では、特定のビット パターンを使用してこれら値を符号化します。IEC 60559 規格での -0.00.0 など、等しい浮動小数点値がそれぞれのオブジェクト表現では異なるビット パターンをもつことがあります。同様に、等しくない浮動小数点値がオブジェクト表現では同じビット パターンをもつこともあります。

修正方法

浮動小数点メンバーを含む構造体を比較する場合、構造体のメンバーを個別に比較します。

2 つの浮動小数点値を比較するには、== または != 演算子を使用します。MISRA™ など、これらの演算子の使用を推奨していない規格に従う場合は、浮動小数点値間の差が許容範囲内に収まるようにします。

例 - memcmp を使用した浮動小数点メンバーをもつ構造体の比較
#include <string.h> 

typedef struct {
    int i;
    float f;
} myStruct;

extern void initialize_Struct(myStruct *);

int func_cmp(myStruct *s1, myStruct *s2) {
/* Comparison between structures containing 
* floating-point members */
    return memcmp  //Noncompliant
        ((const void *)s1, (const void *)s2, sizeof(myStruct));
}

void func(void) {
    myStruct s1, s2;
    initialize_Struct(&s1);
    initialize_Struct(&s2);
    (void)func_cmp(&s1, &s2);
}

この例では、func_cmp()memcmp() を呼び出して、構造体 s1 および s2 のオブジェクト表現を比較しています。この比較は、構造体に浮動小数点メンバーが含まれているため、正確ではない可能性があります。

修正 — 構造体メンバーを個別に比較

1 つの修正方法として、構造体メンバーを個別に比較し、浮動小数点値間の差が ESP で定義された許容範囲内に収まるようにします。

 #include <string.h> 

typedef struct {
    int i;
    float f;
} myStruct;

extern void initialize_Struct(myStruct *);

#define ESP 0.00001

int func_cmp(myStruct *s1, myStruct *s2) {

/*Structure members are compared individually */	
    return ((s1->i == s2->i) &&
            (fabsf(s1->f - s2->f) <= ESP)); 
}

void func(void) {
    myStruct s1, s2;
    initialize_Struct(&s1);
    initialize_Struct(&s2);
    (void)func_cmp(&s1, &s2);
}

チェック情報

グループ: Rule 05.浮動小数点 (FLP)

バージョン履歴

R2019a で導入


1 This software has been created by MathWorks incorporating portions of: the “SEI CERT-C Website,” © 2017 Carnegie Mellon University, the SEI CERT-C++ Web site © 2017 Carnegie Mellon University, ”SEI CERT C Coding Standard – Rules for Developing safe, Reliable and Secure systems – 2016 Edition,” © 2016 Carnegie Mellon University, and “SEI CERT C++ Coding Standard – Rules for Developing safe, Reliable and Secure systems in C++ – 2016 Edition” © 2016 Carnegie Mellon University, with special permission from its Software Engineering Institute.

ANY MATERIAL OF CARNEGIE MELLON UNIVERSITY AND/OR ITS SOFTWARE ENGINEERING INSTITUTE CONTAINED HEREIN IS FURNISHED ON AN "AS-IS" BASIS. CARNEGIE MELLON UNIVERSITY MAKES NO WARRANTIES OF ANY KIND, EITHER EXPRESSED OR IMPLIED, AS TO ANY MATTER INCLUDING, BUT NOT LIMITED TO, WARRANTY OF FITNESS FOR PURPOSE OR MERCHANTABILITY, EXCLUSIVITY, OR RESULTS OBTAINED FROM USE OF THE MATERIAL. CARNEGIE MELLON UNIVERSITY DOES NOT MAKE ANY WARRANTY OF ANY KIND WITH RESPECT TO FREEDOM FROM PATENT, TRADEMARK, OR COPYRIGHT INFRINGEMENT.

This software and associated documentation has not been reviewed nor is it endorsed by Carnegie Mellon University or its Software Engineering Institute.