☰
  • 首页
  • 规则分类
  • 项目介绍
search
•••

对位域声明合理的类型

6.9.1 ID_improperBitfieldType
目录 › next › previous

为了提高可移植性和可维护性,应对位域声明合理的类型,如:

  • 显式声明 signed 或 unsigned 的整数类型
  • C++ 语言的 bool 或 C 语言的 _Bool 类型
  • 各种实现中取值范围均一致的整数类型

C90 标准只允许 int、signed int 或 unsigned int 作为位域类型,在之后的 C 标准以及 C++14 之前的 C++ 标准中,用于位域的 char、short、int、long 或 long long 等整数类型是否有符号由实现定义。

为了避免意料之外的符号扩展、溢出等问题,建议统一使用无符号整型作为位域类型。

示例:

struct A {
    char c: 2;   // Non-compliant
};

char 是否有符号由实现定义,位域 c 的取值范围可能是 [-2, 1] 也可能是 [0, 3],故应明确声明位域的符号属性:

struct A {
    unsigned char c: 2;   // Compliant, or use uint8_t
};

又如:

struct B {
    unsigned long a: 4;    // Bad
    unsigned long b: 32;   // Bad
    unsigned long c: 24;   // Bad
};

例中结构体只涉及 60 个比特位,但由于 long 的取值范围是由实现定义的,结构体的内存布局在不同的平台上会有较大差异,可能会产生意料之外的填充数据,造成对接口或协议的解析错误。

应改为:

#include <stdint.h>   // Or <cstdint> in C++

struct B {
    uint64_t a: 4;    // OK
    uint64_t b: 32;   // OK
    uint64_t c: 24;   // OK
};

配置

bitfieldMustBeUnsigned: 位域类型是否必须为无符号整型 bitfieldMustBeStdInt: 位域类型是否必须为 stdint.h 或 cstdint 中定义的类型

依据

ISO/IEC 9899:1990 6.5.2.1 ISO/IEC 9899:1999 J.3.9(1)-implementation ISO/IEC 9899:2011 J.3.9(1)-implementation ISO/IEC 14882:2003 9.6(3)-implementation ISO/IEC 14882:2011 9.6(3)-implementation

参考

MISRA C 2004 6.4 MISRA C 2012 6.1 MISRA C++ 2008 9-6-2
Copyright©2024 360 Security Technology Inc., Licensed under the Apache-2.0 license.