PORTING.UNSIGNEDCHAR.OVERFLOW.TRUE

关系表达式可能始终为真

PORTING 检查器会标识那些可能依赖于不同编译器中特定实施细则的代码。PORTING.UNSIGNEDCHAR.OVERFLOW.TRUE 检查器检测那些根据"char"类型的符号规范将导致关系表达式可能始终为真的情况。

漏洞与风险

char 数据类型并未在 C 标准中进行精确的定义,因此某个实例可能被视为有符号,也可能被视为无符号。某些编译器允许使用编译器选项来转换 char 的符号,但开发人员的最佳做法是始终编写无歧义的代码,以避免移植代码时出现问题。

缓解与预防

始终指定"char"类型是否有符号。最好是使用 typedef 或 #define 定义,然后在各处都严格执行该定义。

漏洞代码示例

复制
/* print a string replacing any non-ASCII characters with ? */
   void safe_print(char *s) {
     for (; *s; s++) {
       if (*s < 128) {    /* PORTING.UNSIGNEDCHAR.OVERFLOW.TRUE */
         putchar(*s);
       } else {
         putchar('?');
       }
     }
   }
  int main() {
    safe_print("na\xEFve\n"); /* "naïve" in Latin-1 character set */
    return 0;
  }

safe_print() 只能针对无符号的 char 正确作用。

修正代码示例

复制
/* print a string replacing any non-ASCII characters with ? */
   void safe_print(unsigned char *s) {
     for (; *s; s++) {
       if (*s < 128) {    
         putchar(*s);
       } else {
         putchar('?');
       }
     }
   }
  int main() {
    safe_print("na\xEFve\n"); /* "naïve" in Latin-1 character set */
    return 0;
  }

在经修复的示例中,在函数参数声明内,char 被更改为 unsigned char